gibson v2 initial commit
This commit is contained in:
parent
faec62bbbe
commit
472b4c70a6
165
build.sh
165
build.sh
|
@ -1,165 +0,0 @@
|
|||
#!/bin/bash
|
||||
|
||||
verify_cuda() {
|
||||
export CUDA_HOME=/usr/local/cuda-8.0
|
||||
export LD_LIBRARY_PATH=${CUDA_HOME}/lib64
|
||||
|
||||
PATH=${CUDA_HOME}/bin:${PATH}
|
||||
export PATH
|
||||
|
||||
cuda-install-samples-8.0.sh ~/
|
||||
cd ~/NVIDIA_CUDA-8.0_Samples/1\_Utilities/deviceQuery
|
||||
make --quiet
|
||||
./deviceQuery | grep "Result = PASS" &
|
||||
greprc=$?
|
||||
if [[ $greprc -eq 0 ]] ; then
|
||||
echo "Cuda Samples installed and GPU found"
|
||||
echo "you can also check usage and temperature of gpus with nvidia-smi"
|
||||
else
|
||||
if [[ $greprc -eq 1 ]] ; then
|
||||
echo "Cuda Samples not installed, exiting..."
|
||||
exit 1
|
||||
else
|
||||
echo "Some sort of error, exiting..."
|
||||
exit 1
|
||||
fi
|
||||
fi
|
||||
cd -
|
||||
}
|
||||
|
||||
|
||||
cast_error() {
|
||||
if (($? > 0)); then
|
||||
printf '%s\n' "$1" >&2
|
||||
exit 1
|
||||
fi
|
||||
}
|
||||
|
||||
|
||||
verify_conda() {
|
||||
## Conda environment
|
||||
echo 'Checking if conda environment is installed'
|
||||
conda --version
|
||||
if (($? > 0)); then
|
||||
printf 'Installing conda'
|
||||
echo 'export PATH=/opt/conda/bin:$PATH' > /etc/profile.d/conda.sh && \
|
||||
wget --quiet https://repo.continuum.io/miniconda/Miniconda2-4.3.21-Linux-x86_64.sh -O ~/miniconda.sh && \
|
||||
/bin/bash ~/miniconda.sh -b -p /opt/conda && \
|
||||
rm ~/miniconda.sh
|
||||
export PATH=~/opt/conda/bin:$PATH
|
||||
|
||||
alias conda="~/opt/conda/bin/conda"
|
||||
else
|
||||
echo 'conda already installed'
|
||||
fi
|
||||
}
|
||||
|
||||
install() {
|
||||
set -e
|
||||
|
||||
echo -n Password:
|
||||
read -s password
|
||||
|
||||
## Core rendering functionality
|
||||
#conda install -c menpo opencv -y
|
||||
pip install opencv-python ## python3
|
||||
conda install pytorch torchvision cuda80 -c soumith -y
|
||||
|
||||
git clone https://github.com/openai/baselines.git
|
||||
cd baselines
|
||||
pip install -e .
|
||||
## need to remove one line from baseline
|
||||
cd -
|
||||
|
||||
## Core multi channel GLFW
|
||||
echo $password | sudo -s apt-get update
|
||||
echo $password | sudo -s apt-get install libzmq3-dev libglew-dev libglm-dev libassimp-dev xorg-dev libglu1-mesa-dev libboost-dev -y
|
||||
echo $password | sudo -s apt install mesa-common-dev libglu1-mesa-dev freeglut3-dev libopenmpi-dev -y
|
||||
echo $password | sudo -s apt autoremove
|
||||
echo $password | sudo -s apt install cmake -y
|
||||
echo $password | sudo -s apt install golang libjpeg-turbo8-dev unzip -y
|
||||
echo $password | sudo -s apt install wmctrl xdotool -y
|
||||
echo $password | sudo -s apt install libfreeimageplus3 libfreeimageplus-dev libfreeimage3 libfreeimage-dev -y
|
||||
|
||||
## Core renderer
|
||||
echo $password | sudo -s apt install nvidia-cuda-toolkit -y ## Huge, 1121M
|
||||
|
||||
build_local
|
||||
|
||||
download_data
|
||||
}
|
||||
|
||||
build_local() {
|
||||
## Core renderer
|
||||
if [ ! -d ./gibson/core/channels/external/glfw-3.1.2 ]; then
|
||||
wget --quiet https://github.com/glfw/glfw/releases/download/3.1.2/glfw-3.1.2.zip
|
||||
unzip glfw-3.1.2.zip && rm glfw-3.1.2.zip
|
||||
mv glfw-3.1.2 ./gibson/core/channels/external/glfw-3.1.2
|
||||
fi
|
||||
[ ! -d ./gibson/core/channels/build ] || rm -rf ./gibson/core/channels/build
|
||||
|
||||
mkdir -p ./gibson/core/channels/build
|
||||
cd ./gibson/core/channels/build
|
||||
cmake -DCMAKE_BUILD_TYPE=Debug .. && make clean && make -j 10
|
||||
cd -
|
||||
|
||||
|
||||
cd ./gibson/core/render/
|
||||
bash build_cuda.sh
|
||||
cd -
|
||||
}
|
||||
|
||||
decompress_data () {
|
||||
cd gibson
|
||||
tar -zxf assets.tar.gz
|
||||
rm assets.tar.gz
|
||||
if [ -f "gibson/assets/*.pkl" ]; then
|
||||
rm gibson/assets/*.pkl
|
||||
fi
|
||||
cd -
|
||||
}
|
||||
|
||||
|
||||
ec2_install_conda() {
|
||||
if [ ! -d ~/miniconda2 ]; then
|
||||
wget --quiet https://repo.continuum.io/miniconda/Miniconda2-4.3.21-Linux-x86_64.sh -O ~/miniconda.sh && /bin/bash ~/miniconda.sh -b && rm ~/miniconda.sh
|
||||
fi
|
||||
export PATH=/home/ubuntu/miniconda2/bin:$PATH
|
||||
echo "PATH=/home/ubuntu/miniconda2/bin:$PATH" >> ~/.bashrc
|
||||
echo "Run this command in your aws terminal:"
|
||||
echo " export PATH=/home/ubuntu/miniconda2/bin:$PATH"
|
||||
}
|
||||
|
||||
hello() {
|
||||
echo "hello world"
|
||||
}
|
||||
|
||||
subcommand=$1
|
||||
dset_name=$2
|
||||
case "$subcommand" in
|
||||
"install")
|
||||
install
|
||||
;;
|
||||
"hello" )
|
||||
hello
|
||||
;;
|
||||
"ec2_install_conda")
|
||||
ec2_install_conda
|
||||
;;
|
||||
"verify_cuda")
|
||||
verify_cuda
|
||||
;;
|
||||
"verify_conda")
|
||||
verify_conda
|
||||
;;
|
||||
"decompress_data")
|
||||
decompress_data
|
||||
;;
|
||||
"build_local")
|
||||
build_local
|
||||
;;
|
||||
*)
|
||||
default "$@"
|
||||
exit 1
|
||||
;;
|
||||
esac
|
|
@ -1,19 +0,0 @@
|
|||
**/*.dll
|
||||
**/*.exe
|
||||
build/*
|
||||
bin-*/*
|
||||
distrib/build_*/*
|
||||
**.bak
|
||||
**.orig
|
||||
screenshot.bmp
|
||||
*.pyc
|
||||
Thumbs.db
|
||||
OpenGL-tutorial_v*
|
||||
**.mtl
|
||||
.DS_Store
|
||||
build/
|
||||
distrib/
|
||||
*.obj
|
||||
depth_render
|
||||
glew-1.13.0/
|
||||
glfw-3.1.2/
|
|
@ -1,205 +0,0 @@
|
|||
# CMake entry point
|
||||
cmake_minimum_required (VERSION 3.0)
|
||||
project (Gibson_Environment)
|
||||
|
||||
find_package(OpenGL REQUIRED)
|
||||
find_package(GLUT REQUIRED)
|
||||
|
||||
MESSAGE( STATUS "CMAKE_BINARY_DIR: " ${CMAKE_BINARY_DIR} )
|
||||
MESSAGE( STATUS "CMAKE_SOURCE_DIR: " ${CMAKE_SOURCE_DIR} )
|
||||
|
||||
|
||||
# ------ Cuda
|
||||
find_package(CUDA REQUIRED)
|
||||
include_directories(${CUDA_INCLUDE_DIRS})
|
||||
link_directories(${CUDA_LIBRARY_DIRS})
|
||||
# set(CUDA_SEPARABLE_COMPILATION ON)
|
||||
# set(CUDA_ARCH -gencode arch=compute_35,code=sm_35)
|
||||
# set(CUDA_NVCC_FLAGS ${CUDA_NVCC_FLAGS} ${CUDA_ARCH} -Xcompiler -fPIC -shared -o)
|
||||
set(CUDA_NVCC_FLAGS ${CUDA_NVCC_FLAGS} " --Wno-deprecated-gpu-targets -std=c++11")
|
||||
|
||||
|
||||
if( CMAKE_SOURCE_DIR MATCHES " " )
|
||||
message( "Your Source Directory contains spaces. If you experience problems when compiling, this can be the cause." )
|
||||
endif()
|
||||
if( CMAKE_BINARY_DIR MATCHES " " )
|
||||
message( "Your Build Directory contains spaces. If you experience problems when compiling, this can be the cause." )
|
||||
endif()
|
||||
|
||||
## use this to globally use C++11 with in our project
|
||||
set(CMAKE_CXX_STANDARD 11)
|
||||
|
||||
SET(CMAKE_CXX_FLAGS "-D_MWAITXINTRIN_H_INCLUDED -D_FORCE_INLINES -D__STRICT_ANSI__")
|
||||
|
||||
SET(CMAKE_CXX_FLAGS_DEBUG "-O0")
|
||||
SET(CMAKE_C_FLAGS_DEBUG "-O0")
|
||||
|
||||
## load in pkg-config support
|
||||
find_package(PkgConfig)
|
||||
## use pkg-config to get hints for 0mq locations
|
||||
pkg_check_modules(PC_ZeroMQ QUIET zmq)
|
||||
## use the hint from above to find where 'zmq.hpp' is located
|
||||
find_path(ZeroMQ_INCLUDE_DIR
|
||||
NAMES zmq.hpp
|
||||
PATHS ${PC_ZeroMQ_INCLUDE_DIRS}
|
||||
)
|
||||
|
||||
## use the hint from about to find the location of libzmq
|
||||
find_library(ZeroMQ_LIBRARY
|
||||
NAMES zmq
|
||||
PATHS ${PC_ZeroMQ_LIBRARY_DIRS}
|
||||
)
|
||||
|
||||
find_package(GLEW REQUIRED)
|
||||
if (GLEW_FOUND)
|
||||
include_directories(${GLEW_INCLUDE_DIRS})
|
||||
link_libraries(${GLEW_LIBRARIES})
|
||||
add_definitions(${GLEW_DEFINITIONS})
|
||||
message(${GLEW_LIBRARIES})
|
||||
else()
|
||||
message("GLEW NOT FOUND")
|
||||
endif()
|
||||
|
||||
find_package(ASSIMP REQUIRED)
|
||||
if(ASSIMP_FOUND)
|
||||
include_directories(${ASSIMP_INCLUDE_DIR})
|
||||
endif()
|
||||
|
||||
|
||||
add_subdirectory (external)
|
||||
|
||||
add_definitions(-DGLEW_EGL)
|
||||
|
||||
include_directories(
|
||||
${GLEW_INCLUDE_DIRS}
|
||||
external/glfw-3.1.2/include/GLFW
|
||||
external/lodepng/
|
||||
${GLUT_INCLUDE_DIRS}
|
||||
.
|
||||
${ZeroMQ_INCLUDE_DIR}
|
||||
glad
|
||||
)
|
||||
|
||||
|
||||
set(ALL_LIBS
|
||||
${OPENGL_LIBRARY}
|
||||
${GLEW_LIBRARY}
|
||||
GLEW_1130
|
||||
${GLUT_LIBRARY}
|
||||
${ZeroMQ_LIBRARY}
|
||||
glfw
|
||||
dl
|
||||
pthread
|
||||
)
|
||||
|
||||
add_definitions(
|
||||
-DTW_STATIC
|
||||
-DTW_NO_LIB_PRAGMA
|
||||
-DTW_NO_DIRECT3D
|
||||
-DGLEW_STATIC
|
||||
-D_CRT_SECURE_NO_WARNINGS
|
||||
)
|
||||
|
||||
|
||||
|
||||
cuda_add_executable(depth_render
|
||||
glad/egl.c glad/gl.c
|
||||
depth_render/render.cpp
|
||||
common/render_cuda_f.cu
|
||||
common/render_cuda_f.h
|
||||
common/shader.cpp
|
||||
common/shader.hpp
|
||||
common/controls.cpp
|
||||
common/controls.hpp
|
||||
common/MTLtexture.cpp
|
||||
common/MTLtexture.hpp
|
||||
common/texture.cpp
|
||||
common/texture.hpp
|
||||
common/MTLobjloader.cpp
|
||||
common/MTLobjloader.hpp
|
||||
common/MTLplyloader.cpp
|
||||
common/MTLplyloader.hpp
|
||||
common/objloader.cpp
|
||||
common/objloader.hpp
|
||||
common/tinyply.cpp
|
||||
common/tinyply.h
|
||||
common/vboindexer.cpp
|
||||
common/vboindexer.hpp
|
||||
common/text2D.hpp
|
||||
common/text2D.cpp
|
||||
common/picojson.h
|
||||
common/cmdline.h
|
||||
common/semantic_color.hpp
|
||||
external/lodepng/lodepng.h
|
||||
external/lodepng/lodepng.cpp
|
||||
depth_render/StandardShadingRTT.vertexshader
|
||||
depth_render/MistShadingRTT.fragmentshader
|
||||
depth_render/NormalShadingRTT.fragmentshader
|
||||
depth_render/Passthrough.vertexshader
|
||||
depth_render/WobblyTexture.fragmentshader
|
||||
)
|
||||
|
||||
|
||||
target_link_libraries(depth_render
|
||||
${ALL_LIBS}
|
||||
)
|
||||
|
||||
# Xcode and Visual working directories
|
||||
set_target_properties(depth_render PROPERTIES XCODE_ATTRIBUTE_CONFIGURATION_BUILD_DIR "${CMAKE_CURRENT_SOURCE_DIR}/depth_render/")
|
||||
|
||||
|
||||
SOURCE_GROUP(common REGULAR_EXPRESSION ".*/common/.*" )
|
||||
SOURCE_GROUP(shaders REGULAR_EXPRESSION ".*/.*shader$" )
|
||||
|
||||
|
||||
add_custom_command(
|
||||
TARGET depth_render POST_BUILD
|
||||
COMMAND ${CMAKE_COMMAND} -E copy "${CMAKE_CURRENT_BINARY_DIR}/${CMAKE_CFG_INTDIR}/depth_render${CMAKE_EXECUTABLE_SUFFIX}" "${CMAKE_CURRENT_SOURCE_DIR}/depth_render/"
|
||||
)
|
||||
|
||||
|
||||
|
||||
|
||||
cuda_add_executable(semantic
|
||||
glad/egl.c
|
||||
glad/gl.c
|
||||
depth_render/semantic.cpp
|
||||
common/controls.cpp
|
||||
common/controls.hpp
|
||||
common/MTLtexture.cpp
|
||||
common/MTLtexture.hpp
|
||||
common/MTLobjloader.cpp
|
||||
common/MTLobjloader.hpp
|
||||
common/MTLplyloader.cpp
|
||||
common/MTLplyloader.hpp
|
||||
common/objloader.cpp
|
||||
common/objloader.hpp
|
||||
common/tinyply.cpp
|
||||
common/tinyply.h
|
||||
common/vboindexer.cpp
|
||||
common/vboindexer.hpp
|
||||
common/picojson.h
|
||||
common/cmdline.h
|
||||
common/semantic_color.hpp
|
||||
|
||||
external/lodepng/lodepng.h
|
||||
external/lodepng/lodepng.cpp
|
||||
)
|
||||
|
||||
|
||||
target_link_libraries(semantic
|
||||
${ALL_LIBS}
|
||||
)
|
||||
|
||||
# Xcode and Visual working directories
|
||||
set_target_properties(semantic PROPERTIES XCODE_ATTRIBUTE_CONFIGURATION_BUILD_DIR "${CMAKE_CURRENT_SOURCE_DIR}/depth_render/")
|
||||
|
||||
|
||||
SOURCE_GROUP(common REGULAR_EXPRESSION ".*/common/.*" )
|
||||
SOURCE_GROUP(shaders REGULAR_EXPRESSION ".*/.*shader$" )
|
||||
|
||||
|
||||
add_custom_command(
|
||||
TARGET semantic POST_BUILD
|
||||
COMMAND ${CMAKE_COMMAND} -E copy "${CMAKE_CURRENT_BINARY_DIR}/${CMAKE_CFG_INTDIR}/semantic${CMAKE_EXECUTABLE_SUFFIX}" "${CMAKE_CURRENT_SOURCE_DIR}/depth_render/"
|
||||
)
|
|
@ -1,83 +0,0 @@
|
|||
# Find the FreeImage library.
|
||||
#
|
||||
# This module defines
|
||||
# FREEIMAGE_FOUND - True if FREEIMAGE was found.
|
||||
# FREEIMAGE_INCLUDE_DIRS - Include directories for FREEIMAGE headers.
|
||||
# FREEIMAGE_LIBRARIES - Libraries for FREEIMAGE.
|
||||
#
|
||||
# To specify an additional directory to search, set FREEIMAGE_ROOT.
|
||||
#
|
||||
# Copyright (c) 2010, Ewen Cheslack-Postava
|
||||
# Based on FindSQLite3.cmake by:
|
||||
# Copyright (c) 2006, Jaroslaw Staniek, <js@iidea.pl>
|
||||
# Extended by Siddhartha Chaudhuri, 2008.
|
||||
#
|
||||
# Redistribution and use is allowed according to the terms of the BSD license.
|
||||
#
|
||||
|
||||
SET(FREEIMAGE_FOUND FALSE)
|
||||
SET(FREEIMAGE_INCLUDE_DIRS)
|
||||
SET(FREEIMAGE_LIBRARIES)
|
||||
|
||||
SET(SEARCH_PATHS
|
||||
$ENV{ProgramFiles}/freeimage/include
|
||||
$ENV{SystemDrive}/freeimage/include
|
||||
$ENV{ProgramFiles}/freeimage
|
||||
$ENV{SystemDrive}/freeimage
|
||||
)
|
||||
IF(FREEIMAGE_ROOT)
|
||||
SET(SEARCH_PATHS
|
||||
${FREEIMAGE_ROOT}
|
||||
${FREEIMAGE_ROOT}/include
|
||||
${SEARCH_PATHS}
|
||||
)
|
||||
ENDIF()
|
||||
|
||||
FIND_PATH(FREEIMAGE_INCLUDE_DIRS
|
||||
NAMES FreeImage.h
|
||||
PATHS ${SEARCH_PATHS}
|
||||
NO_DEFAULT_PATH)
|
||||
IF(NOT FREEIMAGE_INCLUDE_DIRS) # now look in system locations
|
||||
FIND_PATH(FREEIMAGE_INCLUDE_DIRS NAMES FreeImage.h)
|
||||
ENDIF(NOT FREEIMAGE_INCLUDE_DIRS)
|
||||
|
||||
SET(FREEIMAGE_LIBRARY_DIRS)
|
||||
IF(FREEIMAGE_ROOT)
|
||||
SET(FREEIMAGE_LIBRARY_DIRS ${FREEIMAGE_ROOT})
|
||||
IF(EXISTS "${FREEIMAGE_ROOT}/lib")
|
||||
SET(FREEIMAGE_LIBRARY_DIRS ${FREEIMAGE_LIBRARY_DIRS} ${FREEIMAGE_ROOT}/lib)
|
||||
ENDIF()
|
||||
IF(EXISTS "${FREEIMAGE_ROOT}/lib/static")
|
||||
SET(FREEIMAGE_LIBRARY_DIRS ${FREEIMAGE_LIBRARY_DIRS} ${FREEIMAGE_ROOT}/lib/static)
|
||||
ENDIF()
|
||||
ENDIF()
|
||||
|
||||
# FREEIMAGE
|
||||
# Without system dirs
|
||||
FIND_LIBRARY(FREEIMAGE_LIBRARY
|
||||
NAMES freeimage
|
||||
PATHS ${FREEIMAGE_LIBRARY_DIRS}
|
||||
NO_DEFAULT_PATH
|
||||
)
|
||||
IF(NOT FREEIMAGE_LIBRARY) # now look in system locations
|
||||
FIND_LIBRARY(FREEIMAGE_LIBRARY NAMES freeimage)
|
||||
ENDIF(NOT FREEIMAGE_LIBRARY)
|
||||
|
||||
SET(FREEIMAGE_LIBRARIES)
|
||||
IF(FREEIMAGE_LIBRARY)
|
||||
SET(FREEIMAGE_LIBRARIES ${FREEIMAGE_LIBRARY})
|
||||
ENDIF()
|
||||
|
||||
IF(FREEIMAGE_INCLUDE_DIRS AND FREEIMAGE_LIBRARIES)
|
||||
SET(FREEIMAGE_FOUND TRUE)
|
||||
IF(NOT FREEIMAGE_FIND_QUIETLY)
|
||||
MESSAGE(STATUS "Found FreeImage: headers at ${FREEIMAGE_INCLUDE_DIRS}, libraries at ${FREEIMAGE_LIBRARY_DIRS} :: ${FREEIMAGE_LIBRARIES}")
|
||||
ENDIF(NOT FREEIMAGE_FIND_QUIETLY)
|
||||
ELSE(FREEIMAGE_INCLUDE_DIRS AND FREEIMAGE_LIBRARIES)
|
||||
SET(FREEIMAGE_FOUND FALSE)
|
||||
IF(FREEIMAGE_FIND_REQUIRED)
|
||||
MESSAGE(STATUS "FreeImage not found")
|
||||
ENDIF(FREEIMAGE_FIND_REQUIRED)
|
||||
ENDIF(FREEIMAGE_INCLUDE_DIRS AND FREEIMAGE_LIBRARIES)
|
||||
|
||||
MARK_AS_ADVANCED(FREEIMAGE_INCLUDE_DIRS FREEIMAGE_LIBRARIES)
|
|
@ -1,88 +0,0 @@
|
|||
#
|
||||
# Module for finding FreeImagePlus
|
||||
#
|
||||
# The module will define:
|
||||
# FreeImagePlus_FOUND - True if FreeImagePlus development files were found
|
||||
# FREEIMAGEPLUS_INCLUDE_DIR - FreeImagePlus include directories
|
||||
# FREEIMAGEPLUS_LIBRARY - FreeImagePlus libraries to link
|
||||
#
|
||||
# FreeImagePlus target will be created for cmake 3.0.0 and newer
|
||||
# from https://github.com/myint/perceptualdiff/blob/master/CMakeLists.txt + https://github.com/dormon/FitGL/blob/master/CMakeModules/FindFreeImagePlus.cmake
|
||||
|
||||
|
||||
# try config-based find first
|
||||
find_package(${CMAKE_FIND_PACKAGE_NAME} ${${CMAKE_FIND_PACKAGE_NAME}_FIND_VERSION} CONFIG QUIET)
|
||||
|
||||
# use regular old-style approach
|
||||
if(NOT ${CMAKE_FIND_PACKAGE_NAME}_FOUND)
|
||||
|
||||
if(WIN32)
|
||||
|
||||
find_path(FREEIMAGEPLUS_INCLUDE_DIR FreeImagePlus.h
|
||||
${FREEIMAGEPLUS_ROOT_DIR}/include
|
||||
${FREEIMAGEPLUS_ROOT_DIR}
|
||||
DOC "The directory where FreeImagePlus.h resides")
|
||||
|
||||
find_library(FREEIMAGEPLUS_LIBRARY
|
||||
NAMES FreeImagePlus freeimageplus
|
||||
PATHS
|
||||
${FREEIMAGEPLUS_ROOT_DIR}/lib
|
||||
${FREEIMAGEPLUS_ROOT_DIR}
|
||||
DOC "The FreeImagePlus library")
|
||||
|
||||
else()
|
||||
|
||||
find_path(FREEIMAGEPLUS_INCLUDE_DIR FreeImagePlus.h
|
||||
/usr/include
|
||||
/usr/local/include
|
||||
/sw/include
|
||||
/opt/local/include
|
||||
DOC "The directory where FreeImagePlus.h resides")
|
||||
|
||||
find_library(FREEIMAGEPLUS_LIBRARY
|
||||
NAMES FreeImagePlus freeimageplus
|
||||
PATHS
|
||||
/usr/lib64
|
||||
/usr/lib
|
||||
/usr/local/lib64
|
||||
/usr/local/lib
|
||||
/sw/lib
|
||||
/opt/local/lib
|
||||
DOC "The FreeImagePlus library")
|
||||
|
||||
endif()
|
||||
|
||||
# set *_FOUND flag
|
||||
if(FREEIMAGEPLUS_INCLUDE_DIR AND FREEIMAGEPLUS_LIBRARY)
|
||||
set(${CMAKE_FIND_PACKAGE_NAME}_FOUND True)
|
||||
endif()
|
||||
|
||||
# target for cmake 3.0.0 and newer
|
||||
if(${CMAKE_FIND_PACKAGE_NAME}_FOUND)
|
||||
if(NOT ${CMAKE_MAJOR_VERSION} LESS 3)
|
||||
if(NOT TARGET ${CMAKE_FIND_PACKAGE_NAME})
|
||||
add_library(${CMAKE_FIND_PACKAGE_NAME} INTERFACE IMPORTED)
|
||||
set_target_properties(${CMAKE_FIND_PACKAGE_NAME} PROPERTIES
|
||||
INTERFACE_INCLUDE_DIRECTORIES "${FREEIMAGEPLUS_INCLUDE_DIR}"
|
||||
INTERFACE_LINK_LIBRARIES "${FREEIMAGEPLUS_LIBRARY}"
|
||||
)
|
||||
endif()
|
||||
endif()
|
||||
endif()
|
||||
|
||||
endif()
|
||||
|
||||
# message
|
||||
IF(FREEIMAGEPLUS_INCLUDE_DIR AND FREEIMAGEPLUS_LIBRARY)
|
||||
SET(FREEIMAGEPLUS_FOUND TRUE)
|
||||
IF(NOT FREEIMAGEPLUS_FIND_QUIETLY)
|
||||
MESSAGE(STATUS "Found FreeImagePlus: headers at ${FREEIMAGEPLUS_INCLUDE_DIR}, libraries at ${FREEIMAGEPLUS_LIBRARY}")
|
||||
ENDIF(NOT FREEIMAGEPLUS_FIND_QUIETLY)
|
||||
ELSE(FREEIMAGEPLUS_INCLUDE_DIR AND FREEIMAGEPLUS_LIBRARY)
|
||||
SET(FREEIMAGEPLUS_FOUND FALSE)
|
||||
IF(FREEIMAGEPLUS_FIND_REQUIRED)
|
||||
MESSAGE(STATUS "FreeImagePlus not found")
|
||||
ENDIF(FREEIMAGEPLUS_FIND_REQUIRED)
|
||||
ENDIF(FREEIMAGEPLUS_INCLUDE_DIR AND FREEIMAGEPLUS_LIBRARY)
|
||||
|
||||
MARK_AS_ADVANCED(FREEIMAGEPLUS_INCLUDE_DIR FREEIMAGEPLUS_LIBRARY)
|
|
@ -1,55 +0,0 @@
|
|||
## Universe Environment Multichannel Renderer
|
||||
Support for real time multichannel input (depth, surface normal, etc), implemented using OpenGL.
|
||||
|
||||
All external libraries have been included. You only need CMake (gcc version <=5) on your computer in order to build
|
||||

|
||||
|
||||
|
||||
### Steps
|
||||
|
||||
#### Install dependencies
|
||||
```shell
|
||||
sudo apt-get install libzmq3-dev libassimp-dev
|
||||
sudo apt-get install libglew-dev
|
||||
sudo apt-get install libglm-dev
|
||||
sudo apt-get install xorg-dev
|
||||
sudo apt-get install mesa-common-dev
|
||||
sudo apt-get install libglu1-mesa-dev freeglut3-dev
|
||||
|
||||
```
|
||||
|
||||
|
||||
|
||||
|
||||
Download models: you *do not* have to download dataset separately for this module. Feel free to skip this step, or refer to https://github.com/fxia22/realenv/tree/physics/realenv/envs. If you want to download models for demonstration purpose, do the following
|
||||
```shell
|
||||
cd {realenv_root}/realenv/envs/channels/depth_render
|
||||
wget https://www.dropbox.com/s/qc6sqqua2r2ht4w/16b32add7aa946f283740b9c1c1646c0.obj
|
||||
wget https://www.dropbox.com/s/w7qdbzmo6pp0466/Q97jUzc1wSS_HIGH.obj
|
||||
wget https://www.dropbox.com/s/gs7vhmanjgao9vy/suzanne.obj
|
||||
```
|
||||
|
||||
Compile C code (this might take a minute or two)
|
||||
```shell
|
||||
cd {realenv_root}/realenv/envs/channels
|
||||
mkdir build && cd build
|
||||
cmake ..
|
||||
make
|
||||
```
|
||||
|
||||
Note: GCC Version, if you get the CMake complaint saying `CUDA on Ubuntu: unsupported GNU version! gcc versions later than 5 are not supported!`, you can try out the following solution
|
||||
|
||||
```shell
|
||||
sudo apt install gcc-4.9 g++-4.9
|
||||
sudo update-alternatives --install /usr/bin/gcc gcc /usr/bin/gcc-6 60 --slave /usr/bin/g++ g++ /usr/bin/g++-6
|
||||
sudo update-alternatives --install /usr/bin/gcc gcc /usr/bin/gcc-4.9 50 --slave /usr/bin/g++ g++ /usr/bin/g++-4.9
|
||||
update-alternatives --list gcc
|
||||
update-alternatives --set gcc /usr/bin/gcc-4.9
|
||||
```
|
||||
|
||||
|
||||
Finally, you're done. Although Multichannel Renderer is not supposed to be run on its own, you can do the following to get a sense of it.
|
||||
```
|
||||
cd {realenv_root}/realenv/envs/channels/depth_render
|
||||
./demo
|
||||
```
|
|
@ -1,83 +0,0 @@
|
|||
from PIL import Image
|
||||
import numpy as np
|
||||
import matplotlib.mlab as mlab
|
||||
import matplotlib.pyplot as plt
|
||||
|
||||
#opengl_path = "/home/jerry/Pictures/point_0_view_2_domain_fixatedpose.png"
|
||||
|
||||
opengl_path = "/home/jerry/Pictures/point_0_view_2_domain_fixatedpose_mist.png"
|
||||
#blender_path = "/home/jerry/Desktop/Data/1CzjpjNF8qk/depth/point_0_view_2_domain_depth.png"
|
||||
blender_path = "/home/jerry/Desktop/Data/1CzjpjNF8qk/mist/point_0_view_2_domain_mist.png"
|
||||
|
||||
outline_path = "/home/jerry/Pictures/point_0_view_2_domain_outline.png"
|
||||
|
||||
opengl_viz = "/home/jerry/Pictures/point_0_view_2_domain_viz.png"
|
||||
|
||||
opengl_img = Image.open(opengl_path)
|
||||
blender_img = Image.open(blender_path)
|
||||
|
||||
|
||||
opengl_arr = np.asarray(opengl_img)
|
||||
blender_arr = np.asarray(blender_img)
|
||||
|
||||
## Opengl: opengl_arr[:, :, 0]
|
||||
## Blender: blender_arr
|
||||
|
||||
#opengl_arr = opengl_arr[:, :, 0].reshape((1, -1))[0] ## fpa version
|
||||
|
||||
|
||||
# quick fix for visualization
|
||||
## TODO: cpp png saving upside down
|
||||
#opengl_arr
|
||||
opengl_arr = opengl_arr[::-1][:]
|
||||
#print(opengl_arr.shape, blender_arr.shape)
|
||||
|
||||
|
||||
outline_arr = opengl_arr.copy()
|
||||
|
||||
for row in range(opengl_arr.shape[0]):
|
||||
for col in range(opengl_arr.shape[1]):
|
||||
if np.abs(opengl_arr[row][col] - blender_arr[row][col]) > 3:
|
||||
print(opengl_arr[row][col], blender_arr[row][col])
|
||||
outline_arr[row][col] = 65535
|
||||
|
||||
|
||||
im = Image.new('L', (512, 512))
|
||||
im.putdata(outline_arr.flatten().tolist())
|
||||
im.save(outline_path)
|
||||
|
||||
viz_arr = opengl_arr.copy()
|
||||
viz_arr = viz_arr * 128.0 / 65535
|
||||
viz_arr = np.power(viz_arr, 5)
|
||||
print(viz_arr)
|
||||
|
||||
|
||||
im = Image.new('L', (512, 512))
|
||||
im.putdata(viz_arr.flatten().tolist())
|
||||
im.save(opengl_viz)
|
||||
|
||||
opengl_arr = opengl_arr.reshape((1, -1))[0] ## png version
|
||||
blender_arr = blender_arr.reshape((1, -1))[0]
|
||||
print("before clamping, max blender: ", max(blender_arr))
|
||||
print(opengl_arr)
|
||||
print(np.min(opengl_arr), np.max(opengl_arr), len(opengl_arr))
|
||||
print(np.min(blender_arr),np.max(blender_arr), len(blender_arr))
|
||||
|
||||
diff_count = np.sum((opengl_arr != blender_arr))
|
||||
diff_sqsum = np.sum(np.square(opengl_arr - blender_arr))
|
||||
|
||||
total_count = len(opengl_arr)
|
||||
total_sqsum = np.sum(np.square(opengl_arr))
|
||||
print('How many different', diff_count, float(diff_count) / total_count)
|
||||
print('Total square diff', diff_sqsum, float(diff_sqsum) / total_sqsum)
|
||||
|
||||
blender_arr = blender_arr[blender_arr < 65535]
|
||||
|
||||
plt.subplot(2, 1, 1)
|
||||
n, bins, patches = plt.hist(opengl_arr, 50, normed=1, label='opengl', alpha=0.75)
|
||||
plt.legend(loc='upper right')
|
||||
plt.subplot(2, 1, 2)
|
||||
n, bins, patches = plt.hist(blender_arr, 50, normed=1, label='blender', alpha=0.75)
|
||||
plt.legend(loc='upper right')
|
||||
plt.show()
|
||||
|
|
@ -1,284 +0,0 @@
|
|||
#include <vector>
|
||||
#include <stdio.h>
|
||||
#include <string>
|
||||
#include <cstring>
|
||||
#include <sstream>
|
||||
|
||||
#include <glm/glm.hpp>
|
||||
|
||||
#include "MTLobjloader.hpp"
|
||||
|
||||
// Very, VERY simple OBJ loader.
|
||||
// Here is a short list of features a real function would provide :
|
||||
// - Binary files. Reading a model should be just a few memcpy's away, not parsing a file at runtime. In short : OBJ is not very great.
|
||||
// - Animations & bones (includes bones weights)
|
||||
// - Multiple UVs
|
||||
// - All attributes should be optional, not "forced"
|
||||
// - More stable. Change a line in the OBJ file and it crashes.
|
||||
// - More secure. Change another line and you can inject code.
|
||||
// - Loading from memory, stream, etc
|
||||
|
||||
bool loadOBJ_MTL(
|
||||
const char * path,
|
||||
std::vector<std::vector<glm::vec3>> & out_vertices,
|
||||
std::vector<std::vector<glm::vec2>> & out_uvs,
|
||||
std::vector<std::vector<glm::vec3>> & out_normals,
|
||||
std::vector<glm::vec3> & out_centers,
|
||||
|
||||
std::vector<std::string> & out_material_name,
|
||||
std::string & out_mtllib
|
||||
){
|
||||
printf("Loading OBJ file %s...\n", path);
|
||||
|
||||
std::vector<std::vector<unsigned int>> vertexIndices, uvIndices, normalIndices;
|
||||
std::vector<glm::vec3> temp_vertices;
|
||||
std::vector<glm::vec2> temp_uvs;
|
||||
std::vector<glm::vec3> temp_normals;
|
||||
|
||||
std::vector<unsigned int> temp_vertexIndices;
|
||||
std::vector<unsigned int> temp_uvIndices;
|
||||
std::vector<unsigned int> temp_normalIndices;
|
||||
|
||||
|
||||
FILE * file = fopen(path, "r");
|
||||
if( file == NULL ){
|
||||
printf("Impossible to open the file ! Are you in the right path ? Given path: %s\n", path);
|
||||
getchar();
|
||||
return false;
|
||||
}
|
||||
|
||||
unsigned int v_count = 0;
|
||||
unsigned int mtl_count = 0;
|
||||
std::string last_mtl_name;
|
||||
|
||||
while( 1 ){
|
||||
|
||||
char lineHeader[128];
|
||||
// read the first word of the line
|
||||
int res = fscanf(file, "%s", lineHeader);
|
||||
if (res == EOF)
|
||||
break; // EOF = End Of File. Quit the loop.
|
||||
|
||||
// get mtllib name
|
||||
if ( strcmp( lineHeader, "mtllib") == 0 ){
|
||||
char mtllib;
|
||||
fscanf(file, "%s \n", &mtllib);
|
||||
out_mtllib = &mtllib;
|
||||
//printf("Material Name: %s\n", &mtllib);
|
||||
}
|
||||
//vertices
|
||||
else if ( strcmp( lineHeader, "v" ) == 0 ){
|
||||
v_count ++;
|
||||
glm::vec3 vertex;
|
||||
//fscanf(file, "%f %f %f\n", &vertex.x, &vertex.y, &vertex.z );
|
||||
// opengl = blender rotate around x at 90
|
||||
fscanf(file, "%f %f %f\n", &vertex.x, &vertex.z, &vertex.y);
|
||||
vertex.y = -vertex.y;
|
||||
temp_vertices.push_back(vertex);
|
||||
}
|
||||
// UV
|
||||
else if ( strcmp( lineHeader, "vt" ) == 0 ){
|
||||
glm::vec2 uv;
|
||||
fscanf(file, "%f %f\n", &uv.x, &uv.y );
|
||||
uv.y = -uv.y; // Invert V coordinate since we will only use DDS texture, which are inverted. Remove if you want to use TGA or BMP loaders.
|
||||
temp_uvs.push_back(uv);
|
||||
}
|
||||
// normal
|
||||
else if ( strcmp( lineHeader, "vn" ) == 0 ){
|
||||
glm::vec3 normal;
|
||||
fscanf(file, "%f %f %f\n", &normal.x, &normal.y, &normal.z );
|
||||
temp_normals.push_back(normal);
|
||||
}
|
||||
// material name
|
||||
else if ( strcmp( lineHeader, "usemtl" ) == 0 ){
|
||||
char material_name;
|
||||
fscanf(file, "%s\n", &material_name );
|
||||
std::stringstream ss;
|
||||
std::string tempmat2;
|
||||
ss << &material_name;
|
||||
ss >> tempmat2;
|
||||
//printf("material name: %s, length: %i\n", tempmat2.c_str(), tempmat2.length());
|
||||
out_material_name.push_back(tempmat2.c_str());
|
||||
if (mtl_count > 0) {
|
||||
vertexIndices.push_back(temp_vertexIndices);
|
||||
uvIndices.push_back(temp_uvIndices);
|
||||
normalIndices.push_back(temp_normalIndices);
|
||||
|
||||
temp_vertexIndices.clear();
|
||||
temp_uvIndices.clear();
|
||||
temp_normalIndices.clear();
|
||||
}
|
||||
mtl_count ++;
|
||||
}
|
||||
// face
|
||||
else if ( mtl_count > 0 && strcmp( lineHeader, "f" ) == 0 ){
|
||||
std::string vertex1, vertex2, vertex3;
|
||||
unsigned int vertexIndex[3], uvIndex[3], normalIndex[3];
|
||||
char stringBuffer[500];
|
||||
fgets(stringBuffer, 500, file);
|
||||
//int matches = fscanf(file, "%u/%u/%u %u/%u/%u %u/%u/%u\n", &vertexIndex[0], &uvIndex[0], &normalIndex[0], &vertexIndex[1], &uvIndex[1], &normalIndex[1], &vertexIndex[2], &uvIndex[2], &normalIndex[2] );
|
||||
int matches = sscanf(stringBuffer, "%u/%u/%u %u/%u/%u %u/%u/%u\n", &vertexIndex[0], &uvIndex[0], &normalIndex[0], &vertexIndex[1], &uvIndex[1], &normalIndex[1], &vertexIndex[2], &uvIndex[2], &normalIndex[2] );
|
||||
bool f_3_format = (matches == 9);
|
||||
bool f_2_format = true;
|
||||
if (! f_3_format) {
|
||||
// .obj file has `f v1/uv1 v2/uv2 v3/uv3` format
|
||||
int matches = sscanf(stringBuffer, " %u/%u %u/%u %u/%u\n", &vertexIndex[0], &uvIndex[0], &vertexIndex[1], &uvIndex[1], &vertexIndex[2], &uvIndex[2] );
|
||||
f_2_format = (matches == 6);
|
||||
if (! f_2_format) {
|
||||
matches = sscanf(stringBuffer, " %u %u %u\n", &vertexIndex[0], &vertexIndex[1], &vertexIndex[2]);
|
||||
if (matches != 3){
|
||||
printf("File can't be read by our simple parser :-( Try exporting with other options\n");
|
||||
fclose(file);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
temp_vertexIndices.push_back(vertexIndex[0]);
|
||||
temp_vertexIndices.push_back(vertexIndex[1]);
|
||||
temp_vertexIndices.push_back(vertexIndex[2]);
|
||||
|
||||
if (f_2_format || f_3_format) {
|
||||
temp_uvIndices .push_back(uvIndex[0]);
|
||||
temp_uvIndices .push_back(uvIndex[1]);
|
||||
temp_uvIndices .push_back(uvIndex[2]);
|
||||
}
|
||||
if (f_3_format) {
|
||||
temp_normalIndices.push_back(normalIndex[0]);
|
||||
temp_normalIndices.push_back(normalIndex[1]);
|
||||
temp_normalIndices.push_back(normalIndex[2]);
|
||||
}
|
||||
}
|
||||
// other
|
||||
else {
|
||||
// Probably a comment, eat up the rest of the line
|
||||
char stupidBuffer[1000];
|
||||
fgets(stupidBuffer, 1000, file);
|
||||
}
|
||||
}
|
||||
|
||||
vertexIndices.push_back(temp_vertexIndices);
|
||||
uvIndices.push_back(temp_uvIndices);
|
||||
normalIndices.push_back(temp_normalIndices);
|
||||
temp_vertexIndices.clear();
|
||||
temp_uvIndices.clear();
|
||||
temp_normalIndices.clear();
|
||||
|
||||
// Calculate semantic center position
|
||||
for (unsigned int i=0; i<vertexIndices.size(); i++) {
|
||||
std::vector<unsigned int> vertexIndex_group = vertexIndices[i];
|
||||
glm::vec3 center = glm::vec3(0.0);
|
||||
|
||||
for (unsigned int j=0; j<vertexIndex_group.size();j++) {
|
||||
unsigned int vertexIndex = vertexIndex_group[j];
|
||||
glm::vec3 vertex = temp_vertices[ vertexIndex-1 ];
|
||||
center += vertex / 3.0f;
|
||||
}
|
||||
center /= (vertexIndex_group.size() / 3);
|
||||
out_centers.push_back(center);
|
||||
center = glm::vec3(0.0);
|
||||
}
|
||||
|
||||
// For each vertex of each triangle
|
||||
for( unsigned int i=0; i<vertexIndices.size(); i++ ){
|
||||
std::vector<glm::vec3> temp_out_vertices;
|
||||
std::vector<glm::vec2> temp_out_uvs;
|
||||
std::vector<glm::vec3> temp_out_normals;
|
||||
|
||||
//printf("Vertex group %d size %d\n", i + 1, vertexIndices.size());
|
||||
std::string mat_name = out_material_name[i];
|
||||
/*if (mat_name == "wall_65_hallway_7_1") {
|
||||
for (unsigned int j = 0; j < vertexIndices[i].size(); j++) {
|
||||
printf("%s %d\n", mat_name.c_str(), vertexIndices[i][j]);
|
||||
}
|
||||
}*/
|
||||
for ( unsigned int j=0; j<vertexIndices[i].size(); j++) {
|
||||
// Get the indices of its attributes
|
||||
unsigned int vertexIndex = vertexIndices[i][j];
|
||||
unsigned int uvIndex = -1;
|
||||
|
||||
if (uvIndices.size() > 0 && uvIndices[i].size() > 0)
|
||||
uvIndex = uvIndices[i][j];
|
||||
|
||||
unsigned int normalIndex = -1;
|
||||
if (normalIndices.size() > 0 && normalIndices[i].size() > 0)
|
||||
normalIndex = normalIndices[i][j];
|
||||
|
||||
// Get the attributes thanks to the index
|
||||
glm::vec3 vertex = temp_vertices[ vertexIndex-1 ];
|
||||
|
||||
// Put the attributes in buffers
|
||||
temp_out_vertices.push_back(vertex);
|
||||
|
||||
if (temp_uvs.size() > 0 && uvIndices.size() > 0) {
|
||||
glm::vec2 uv = temp_uvs[ uvIndex-1 ];
|
||||
temp_out_uvs .push_back(uv);
|
||||
}
|
||||
|
||||
if (temp_normals.size() > 0 && normalIndices.size() > 0) {
|
||||
glm::vec3 normal = temp_normals[ normalIndex-1 ];
|
||||
temp_out_normals.push_back(normal);
|
||||
}
|
||||
}
|
||||
out_vertices.push_back(temp_out_vertices);
|
||||
if (temp_out_uvs.size() > 0)
|
||||
out_uvs.push_back(temp_out_uvs);
|
||||
if (temp_out_normals.size() > 0)
|
||||
out_normals.push_back(temp_out_normals);
|
||||
}
|
||||
|
||||
// construct the temp_normals vector here, using vertex positions and face vertex indices
|
||||
// TODO: this is not well-tested yet
|
||||
|
||||
if ( out_normals.size() == 0 ) {
|
||||
for ( unsigned int i=0; i<out_vertices.size(); i++ ){
|
||||
std::vector<glm::vec3> temp_out_normals;
|
||||
for ( unsigned int j=0; j<out_vertices[i].size(); j++ ){
|
||||
temp_out_normals.push_back(glm::vec3(0.0));
|
||||
}
|
||||
out_normals.push_back(temp_out_normals);
|
||||
}
|
||||
|
||||
std::vector<std::vector<unsigned int>> vertexFaces;
|
||||
for ( unsigned int i=0; i<vertexIndices.size(); i++ ){
|
||||
std::vector<unsigned int> temp_vertexFaces(out_vertices[i].size());
|
||||
std::fill(temp_vertexFaces.begin(), temp_vertexFaces.end(), 0);
|
||||
for ( unsigned int j=0; j<vertexIndices[i].size(); j++ ){
|
||||
temp_vertexFaces[vertexIndices[i][j]] += 1;
|
||||
}
|
||||
vertexFaces.push_back(temp_vertexFaces);
|
||||
}
|
||||
|
||||
for ( unsigned int i=0; i<vertexIndices.size(); i++ ){
|
||||
for ( unsigned int j=0; j<vertexIndices[i].size(); j++ ){
|
||||
// make sure vertices are arranged in right hand order
|
||||
unsigned int v1 = j;
|
||||
unsigned int v2 = v1; // ((v1+1)%3==0) ? (v1-2) : (v1+1);
|
||||
unsigned int v3 = v1; //((v2+1)%3==0) ? (v2-2) : (v2+1);
|
||||
|
||||
glm::vec3 edge1 = out_vertices[i][v2] - out_vertices[i][v1];
|
||||
glm::vec3 edge2 = out_vertices[i][v3] - out_vertices[i][v2];
|
||||
|
||||
// set normal as cross product
|
||||
unsigned int vertexIndex = vertexIndices[i][j];
|
||||
glm::vec3 normal = glm::normalize(glm::cross(edge1, edge2));
|
||||
out_normals[i][vertexIndex-1] += normal / float(vertexFaces[i][vertexIndex-1]);
|
||||
//printf("%f %f %f\n", normal[0], normal[1], normal[2]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// TODO: (hzyjerry) this is a dummy place holder
|
||||
if ( out_uvs.size() == 0 ) {
|
||||
for ( unsigned int i=0; i<out_vertices.size(); i++ ){
|
||||
std::vector<glm::vec2> temp_out_uvs;
|
||||
for ( unsigned int j=0; j<out_vertices[i].size(); j++ ){
|
||||
temp_out_uvs.push_back(glm::vec2(0.0));
|
||||
}
|
||||
out_uvs.push_back(temp_out_uvs);
|
||||
}
|
||||
}
|
||||
printf("%s: size of temp vertices %lu, vertex indices %lu out vertices %lu\n", path, temp_vertices.size(), vertexIndices.size(), out_vertices.size());
|
||||
fclose(file);
|
||||
return true;
|
||||
}
|
|
@ -1,15 +0,0 @@
|
|||
#ifndef MTL_OBJLOADER_H
|
||||
#define MTL_OBJLOADER_H
|
||||
|
||||
bool loadOBJ_MTL(
|
||||
const char * path,
|
||||
std::vector<std::vector<glm::vec3>> & out_vertices,
|
||||
std::vector<std::vector<glm::vec2>> & out_uvs,
|
||||
std::vector<std::vector<glm::vec3>> & out_normals,
|
||||
std::vector<glm::vec3> & out_centers,
|
||||
|
||||
std::vector<std::string> & out_material_name,
|
||||
std::string & out_mtllib
|
||||
);
|
||||
|
||||
#endif
|
|
@ -1,428 +0,0 @@
|
|||
// Include standard headers
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string>
|
||||
#include <fstream>
|
||||
#include <iostream>
|
||||
#include <cstdlib> //rand
|
||||
#include <chrono>
|
||||
#include <vector>
|
||||
#include <cstring>
|
||||
#include <sstream>
|
||||
|
||||
#include <glm/glm.hpp>
|
||||
//using namespace glm;
|
||||
using namespace std;
|
||||
typedef std::chrono::time_point<std::chrono::high_resolution_clock> timepoint;
|
||||
|
||||
#include "common/tinyply.h"
|
||||
using namespace tinyply;
|
||||
|
||||
#include "common/picojson.h"
|
||||
#include "common/MTLplyloader.hpp"
|
||||
|
||||
struct float3 { float x, y, z; };
|
||||
struct float2 {int u, v;};
|
||||
struct int3 {int a, b, c;};
|
||||
|
||||
|
||||
inline double difference_millis(timepoint start, timepoint end)
|
||||
{
|
||||
return (double)std::chrono::duration_cast<std::chrono::milliseconds>(end - start).count();
|
||||
}
|
||||
|
||||
std::chrono::high_resolution_clock c;
|
||||
|
||||
inline std::chrono::time_point<std::chrono::high_resolution_clock> now()
|
||||
{
|
||||
return c.now();
|
||||
}
|
||||
|
||||
bool loadPLY(
|
||||
const char * path,
|
||||
std::vector<glm::vec3> & out_vertices,
|
||||
std::vector<glm::vec2> & out_uvs,
|
||||
std::vector<glm::vec3> & out_normals,
|
||||
std::vector<int3> & out_faces,
|
||||
int & num_vertices
|
||||
){
|
||||
|
||||
std::string path_name = path;
|
||||
path_name = path_name + "/semantic.ply";
|
||||
|
||||
std::ifstream ss(path_name, std::ios::binary);
|
||||
if (ss.fail())
|
||||
{
|
||||
throw std::runtime_error("failed to open " + path_name);
|
||||
}
|
||||
|
||||
PlyFile file;
|
||||
file.parse_header(ss);
|
||||
/*
|
||||
for (auto c : file.get_comments()) std::cout << "Comment: " << c << std::endl;
|
||||
for (auto e : file.get_elements())
|
||||
{
|
||||
std::cout << "element - " << e.name << " (" << e.size << ")" << std::endl;
|
||||
for (auto p : e.properties)
|
||||
{
|
||||
std::cout << "\tproperty - " << p.name << " (" << tinyply::PropertyTable[p.propertyType].str << ")" << std::endl;
|
||||
}
|
||||
}
|
||||
*/
|
||||
std::shared_ptr<PlyData> vertices, normals, colors, uvs, faces, texcoords;
|
||||
|
||||
// The header information can be used to programmatically extract properties on elements
|
||||
// known to exist in the file header prior to reading the data. For brevity of this sample, properties
|
||||
// like vertex position are hard-coded:
|
||||
try { vertices = file.request_properties_from_element("vertex", { "x", "y", "z" }); }
|
||||
catch (const std::exception & e) { /*std::cerr << "tinyply exception: " << e.what() << std::endl; */}
|
||||
|
||||
try { normals = file.request_properties_from_element("vertex", { "nx", "ny", "nz" }); }
|
||||
catch (const std::exception & e) { /*std::cerr << "tinyply exception: " << e.what() << std::endl; */}
|
||||
|
||||
try { colors = file.request_properties_from_element("vertex", { "red", "green", "blue", "alpha" }); }
|
||||
catch (const std::exception & e) { /*std::cerr << "tinyply exception: " << e.what() << std::endl; */}
|
||||
|
||||
try { uvs = file.request_properties_from_element("vertex", { "texture_u", "texture_v" }); }
|
||||
catch (const std::exception & e) { /*std::cerr << "tinyply exception: " << e.what() << std::endl; */}
|
||||
|
||||
try { faces = file.request_properties_from_element("face", { "vertex_indices" }); }
|
||||
catch (const std::exception & e) { /*std::cerr << "tinyply exception: " << e.what() << std::endl; */}
|
||||
|
||||
try { texcoords = file.request_properties_from_element("face", { "texcoord" }); }
|
||||
catch (const std::exception & e) { /*std::cerr << "tinyply exception: " << e.what() << std::endl; */}
|
||||
|
||||
timepoint before = now();
|
||||
file.read(ss);
|
||||
timepoint after = now();
|
||||
|
||||
// Good place to put a breakpoint!
|
||||
std::cout << "Parsing took " << difference_millis(before, after) << " ms: " << std::endl;
|
||||
if (vertices) std::cout << "\tRead " << vertices->count << " total vertices "<< std::endl;
|
||||
if (normals) std::cout << "\tRead " << normals->count << " total vertex normals " << std::endl;
|
||||
if (colors) std::cout << "\tRead " << colors->count << " total vertex colors "<< std::endl;
|
||||
if (uvs) std::cout << "\tRead " << uvs->count << " total vertex uvs" << std::endl;
|
||||
if (faces) std::cout << "\tRead " << faces->count << " total faces (triangles) " << std::endl;
|
||||
if (texcoords) std::cout << "\tRead " << texcoords->count << " total texcoords " << std::endl;
|
||||
|
||||
num_vertices = vertices->count;
|
||||
std::vector<float3> v_vertices;
|
||||
std::vector<int3> v_faces;
|
||||
std::vector<float3> v_normals;
|
||||
std::vector<float2> v_uvs;
|
||||
|
||||
v_vertices = std::vector<float3>(vertices->count);
|
||||
v_faces = std::vector<int3>(faces->count);
|
||||
if (normals) v_normals = std::vector<float3>(normals->count);
|
||||
if (uvs) v_uvs = std::vector<float2>(uvs->count);
|
||||
|
||||
// Example: type 'conversion' to your own native types - Option A
|
||||
size_t numVerticesBytes;
|
||||
size_t numNormalBytes;
|
||||
size_t numFaceBytes;
|
||||
size_t numTextureBytes;
|
||||
numVerticesBytes = vertices->buffer.size_bytes();
|
||||
numNormalBytes = normals->buffer.size_bytes();
|
||||
if (normals) numFaceBytes = faces->buffer.size_bytes();
|
||||
if (uvs) numTextureBytes = uvs->buffer.size_bytes();
|
||||
|
||||
std::memcpy(v_vertices.data(), vertices->buffer.get(), numVerticesBytes);
|
||||
std::memcpy(v_faces.data(), faces->buffer.get(), numFaceBytes);
|
||||
if (normals) std::memcpy(v_normals.data(), normals->buffer.get(), numNormalBytes);
|
||||
if (uvs) std::memcpy(v_uvs.data(), uvs->buffer.get(), numTextureBytes);
|
||||
|
||||
float3 temp_vertice;
|
||||
float3 temp_normal;
|
||||
float2 temp_uv;
|
||||
int3 face_i;
|
||||
|
||||
|
||||
for (unsigned int i = 0; i < faces->count; i++)
|
||||
out_faces.push_back(v_faces[i]);
|
||||
|
||||
for (unsigned int i = 0; i < vertices->count; i++) {
|
||||
temp_vertice = v_vertices[i];
|
||||
out_vertices.push_back(glm::vec3(temp_vertice.x, temp_vertice.y, temp_vertice.z));
|
||||
if (normals) {
|
||||
temp_normal = v_normals[i];
|
||||
out_normals.push_back(glm::vec3(temp_normal.x, temp_normal.y, temp_normal.z));
|
||||
}
|
||||
if (uvs) {
|
||||
temp_uv = v_uvs[i];
|
||||
out_uvs.push_back(glm::vec2(temp_uv.u, temp_uv.v));
|
||||
}
|
||||
}
|
||||
/*
|
||||
for (unsigned int i = 0; i < faces->count; i++) {
|
||||
face_i = v_faces[i];
|
||||
//printf("Face coordinates %d/%d (%d %d %d)/%d \n", i, faces->count, face_i.a - 1, face_i.b - 1, face_i.c - 1, vertices->count);
|
||||
temp_vertice = v_vertices[face_i.a - 1];
|
||||
temp_normal = v_normals[face_i.a - 1];
|
||||
temp_uv = v_uvs[face_i.a - 1];
|
||||
out_vertices.push_back(glm::vec3(temp_vertice.x, temp_vertice.y, temp_vertice.z));
|
||||
out_normals.push_back(glm::vec3(temp_normal.x, temp_normal.y, temp_normal.z));
|
||||
out_uvs.push_back(glm::vec2(temp_uv.u, temp_uv.v));
|
||||
//printf("Vertex a (%f %f %f) normal (%f %f %f) uv (%f %f)\n", temp_vertice.x, temp_vertice.y, temp_vertice.z, temp_normal.x, temp_normal.y, temp_normal.z, temp_uv.u, temp_uv.v);
|
||||
|
||||
temp_vertice = v_vertices[face_i.b - 1];
|
||||
temp_normal = v_normals[face_i.b - 1];
|
||||
temp_uv = v_uvs[face_i.b - 1];
|
||||
out_vertices.push_back(glm::vec3(temp_vertice.x, temp_vertice.y, temp_vertice.z));
|
||||
out_normals.push_back(glm::vec3(temp_normal.x, temp_normal.y, temp_normal.z));
|
||||
out_uvs.push_back(glm::vec2(temp_uv.u, temp_uv.v));
|
||||
//printf("Vertex b (%f %f %f) normal (%f %f %f) uv (%f %f)\n", temp_vertice.x, temp_vertice.y, temp_vertice.z, temp_normal.x, temp_normal.y, temp_normal.z, temp_uv.u, temp_uv.v);
|
||||
|
||||
temp_vertice = v_vertices[face_i.c - 1];
|
||||
temp_normal = v_normals[face_i.c - 1];
|
||||
temp_uv = v_uvs[face_i.c - 1];
|
||||
out_vertices.push_back(glm::vec3(temp_vertice.x, temp_vertice.y, temp_vertice.z));
|
||||
out_normals.push_back(glm::vec3(temp_normal.x, temp_normal.y, temp_normal.z));
|
||||
out_uvs.push_back(glm::vec2(temp_uv.u, temp_uv.v));
|
||||
//printf("Vertex c (%f %f %f) normal (%f %f %f) uv (%f %f)\n", temp_vertice.x, temp_vertice.y, temp_vertice.z, temp_normal.x, temp_normal.y, temp_normal.z, temp_uv.u, temp_uv.v);
|
||||
}
|
||||
*/
|
||||
|
||||
return true;
|
||||
|
||||
};
|
||||
|
||||
|
||||
/* Load semantic JSON file for Matterport3D dataset
|
||||
* Require: semantic.fsegs.json, semantic.semseg.json
|
||||
* Output:
|
||||
* out_label_id: list of semantic segment label
|
||||
* out_segment_id: list of segmentic segment id (start from 0, incremental)
|
||||
* out_face_indices: list of semantic groups, each group contains all faces of the segment
|
||||
* Example:
|
||||
* # 0th semantic component
|
||||
* out_label_id[0] = 1 # Semantic id is 1
|
||||
* out_segment_id[0] = 0 # Semantic label index is 0 (start from 0)
|
||||
* out_face_indices[0] = [0, 1, 2] # Face index 0, 1, 2
|
||||
*/
|
||||
bool loadJSONtextures (
|
||||
std::string jsonpath,
|
||||
std::vector<int> & out_label_id,
|
||||
std::vector<int> & out_segment_id,
|
||||
std::vector<std::vector<int>> & out_face_indices
|
||||
) {
|
||||
std::string imagePath;
|
||||
std::string fsegs_json = jsonpath + "/semantic.fsegs.json";
|
||||
std::ifstream ss(fsegs_json, std::ios::binary);
|
||||
if (ss.fail())
|
||||
throw std::runtime_error("failed to open " + fsegs_json);
|
||||
|
||||
std::vector<int> segid_list;
|
||||
std::vector<std::vector<int>> segid_to_index;
|
||||
std::vector<int> index_to_segment_id;
|
||||
std::vector<int> index_to_segment_label_id;
|
||||
|
||||
int max_segid = -1;
|
||||
|
||||
if (ss) {
|
||||
// get length of file:
|
||||
ss.seekg (0, ss.end);
|
||||
int length = ss.tellg();
|
||||
ss.seekg (0, ss.beg);
|
||||
|
||||
char * buffer = new char [length];
|
||||
std::cout << "Reading " << length << " characters... ";
|
||||
ss.read (buffer,length);
|
||||
if (ss)
|
||||
std::cout << "all characters read successfully." << std::endl;
|
||||
else
|
||||
std::cout << "error: only " << ss.gcount() << " could be read" << std::endl;
|
||||
ss.close();
|
||||
|
||||
// ...buffer contains the entire file...
|
||||
picojson::value v;
|
||||
std::string err;
|
||||
const char* json_end = picojson::parse(v, buffer, buffer + strlen(buffer), &err);
|
||||
if (! err.empty())
|
||||
std::cerr << err << std::endl;
|
||||
|
||||
// check if the type of the value is "object"
|
||||
if (! v.is<picojson::object>()) {
|
||||
std::cerr << "JSON is not an object" << std::endl;
|
||||
exit(2);
|
||||
}
|
||||
|
||||
// obtain a const reference to the map, and print the contents
|
||||
picojson::array value_arr;
|
||||
const picojson::value::object& obj = v.get<picojson::object>();
|
||||
for (picojson::value::object::const_iterator i = obj.begin();
|
||||
i != obj.end();
|
||||
++i) {
|
||||
if (i-> first == "segIndices" && i->second.is<picojson::array>()) {
|
||||
value_arr = i->second.get<picojson::array>();
|
||||
}
|
||||
}
|
||||
|
||||
for (unsigned int i = 0; i < value_arr.size(); i++) {
|
||||
int val = (stoi(value_arr[i].to_str()));
|
||||
segid_list.push_back(val);
|
||||
index_to_segment_id.push_back(0);
|
||||
index_to_segment_label_id.push_back(0);
|
||||
if (val > max_segid)
|
||||
max_segid = val;
|
||||
}
|
||||
|
||||
for (unsigned int i = 0; i < max_segid + 1; i++)
|
||||
segid_to_index.push_back(std::vector<int>());
|
||||
for (unsigned int i = 0; i < segid_list.size(); i++) {
|
||||
segid_to_index[segid_list[i]].push_back(i);
|
||||
}
|
||||
|
||||
delete[] buffer;
|
||||
}
|
||||
|
||||
printf("Finished loading indexes: %lu\n", segid_list.size());
|
||||
|
||||
std::string ssegs_json = jsonpath + "/semantic.semseg.json";
|
||||
std::ifstream sg(ssegs_json, std::ios::binary);
|
||||
if (sg.fail())
|
||||
throw std::runtime_error("failed to open " + ssegs_json);
|
||||
|
||||
std::vector<std::vector<int>> seg_groups;
|
||||
if (sg) {
|
||||
// get length of file:
|
||||
sg.seekg (0, sg.end);
|
||||
int length = sg.tellg();
|
||||
sg.seekg (0, sg.beg);
|
||||
|
||||
char * buffer = new char [length];
|
||||
std::cout << "Reading " << length << " characters... ";
|
||||
sg.read (buffer,length);
|
||||
if (sg)
|
||||
std::cout << "all characters read successfully." << std::endl;
|
||||
else
|
||||
std::cout << "error: only " << sg.gcount() << " could be read" << std::endl;
|
||||
sg.close();
|
||||
|
||||
// ...buffer contains the entire file...
|
||||
picojson::value v;
|
||||
std::string err;
|
||||
const char* json_end = picojson::parse(v, buffer, buffer + strlen(buffer), &err);
|
||||
if (! err.empty())
|
||||
std::cerr << err << std::endl;
|
||||
|
||||
// check if the type of the value is "object"
|
||||
if (! v.is<picojson::object>()) {
|
||||
std::cerr << "JSON is not an object" << std::endl;
|
||||
exit(2);
|
||||
}
|
||||
|
||||
// obtain a const reference to the map, and print the contents
|
||||
picojson::array segment_arr;
|
||||
const picojson::value::object& obj = v.get<picojson::object>();
|
||||
for (picojson::value::object::const_iterator i = obj.begin();
|
||||
i != obj.end();
|
||||
++i) {
|
||||
if (i-> first == "segGroups" && i->second.is<picojson::array>()) {
|
||||
segment_arr = i->second.get<picojson::array>();
|
||||
}
|
||||
}
|
||||
|
||||
picojson::array::iterator it;
|
||||
for (it = segment_arr.begin(); it != segment_arr.end(); it++) {
|
||||
picojson::object obj_it = it->get<picojson::object>();
|
||||
int segment_id = stoi(obj_it["id"].to_str());
|
||||
int label_id = stoi(obj_it["label_index"].to_str());
|
||||
// Output to texture name
|
||||
out_label_id.push_back(label_id);
|
||||
out_segment_id.push_back(segment_id);
|
||||
std::vector<int> face_index;
|
||||
|
||||
picojson::value seg_val = obj_it["segments"];
|
||||
picojson::array seg_arr_i;
|
||||
if (seg_val.is<picojson::array>()) {
|
||||
seg_arr_i = seg_val.get<picojson::array>();
|
||||
for (unsigned int i = 0; i < seg_arr_i.size(); i++) {
|
||||
int segid = (stoi(seg_arr_i[i].to_str()));
|
||||
for (unsigned int j = 0; j < segid_to_index[segid].size(); j++) {
|
||||
int index = segid_to_index[segid][j];
|
||||
index_to_segment_id[index] = segment_id;
|
||||
index_to_segment_label_id[index] = label_id;
|
||||
|
||||
face_index.push_back(index);
|
||||
}
|
||||
}
|
||||
}
|
||||
// Output the associated vertex indices for this texture name
|
||||
out_face_indices.push_back(face_index);
|
||||
}
|
||||
delete[] buffer;
|
||||
}
|
||||
|
||||
return true;
|
||||
};
|
||||
|
||||
|
||||
bool loadPLY_MTL(
|
||||
const char * path,
|
||||
std::vector<std::vector<glm::vec3>> & out_vertices,
|
||||
std::vector<std::vector<glm::vec2>> & out_uvs,
|
||||
std::vector<std::vector<glm::vec3>> & out_normals,
|
||||
std::vector<glm::vec3> & out_centers,
|
||||
//std::vector<int> & out_material_name,
|
||||
std::vector<int> & out_material_id,
|
||||
std::string & out_mtllib,
|
||||
int & num_vertices
|
||||
){
|
||||
//printf("Loading OBJ file %s...\n", path);
|
||||
|
||||
std::vector<glm::vec3> all_vertices;
|
||||
std::vector<glm::vec2> all_uvs;
|
||||
std::vector<glm::vec3> all_normals;
|
||||
std::vector<int3> all_faces;
|
||||
|
||||
std::vector<int> label_index; // Actual id in Matterport3D
|
||||
std::vector<int> segment_index;
|
||||
std::vector<std::vector<int>> face_indices; // Auxiliary index
|
||||
loadPLY(path, all_vertices, all_uvs, all_normals, all_faces, num_vertices);
|
||||
loadJSONtextures(path, label_index, segment_index, face_indices);
|
||||
|
||||
bool has_uvs = all_uvs.size() > 0;
|
||||
bool has_normals = all_normals.size() > 0;
|
||||
|
||||
std::cout << "Loaded many faces " << all_faces.size() << std::endl;
|
||||
if (! all_faces.size() == face_indices.size()) {
|
||||
std::cerr << "Your ply object file (" << all_faces.size() << ") does not match with JSON file (" << face_indices.size() << ")." << std::endl;
|
||||
exit(2);
|
||||
}
|
||||
|
||||
for (unsigned int i = 0; i < label_index.size(); i++) {
|
||||
out_material_id.push_back(label_index[i]);
|
||||
std::vector<int> faces = face_indices[i];
|
||||
|
||||
std::vector<glm::vec3> curr_vertices;
|
||||
std::vector<glm::vec2> curr_uvs;
|
||||
std::vector<glm::vec3> curr_normals;
|
||||
glm::vec3 center = glm::vec3(0.0);
|
||||
for (unsigned int j = 0; j < faces.size(); j++) {
|
||||
int face_index = faces[j];
|
||||
int3 curr_face = all_faces[face_index];
|
||||
curr_vertices.push_back(all_vertices[curr_face.a]);
|
||||
curr_vertices.push_back(all_vertices[curr_face.b]);
|
||||
curr_vertices.push_back(all_vertices[curr_face.c]);
|
||||
center += (all_vertices[curr_face.a] + all_vertices[curr_face.b] + all_vertices[curr_face.c]) / 3.0f;
|
||||
if (has_uvs) {
|
||||
curr_uvs.push_back(all_uvs[curr_face.a]);
|
||||
curr_uvs.push_back(all_uvs[curr_face.b]);
|
||||
curr_uvs.push_back(all_uvs[curr_face.c]);
|
||||
}
|
||||
if (has_normals) {
|
||||
curr_normals.push_back(all_normals[curr_face.a]);
|
||||
curr_normals.push_back(all_normals[curr_face.b]);
|
||||
curr_normals.push_back(all_normals[curr_face.c]);
|
||||
}
|
||||
}
|
||||
center /= faces.size();
|
||||
|
||||
out_centers.push_back(center);
|
||||
out_vertices.push_back(curr_vertices);
|
||||
if (has_uvs) out_uvs.push_back(curr_uvs);
|
||||
if (has_normals) out_normals.push_back(curr_normals);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
|
@ -1,26 +0,0 @@
|
|||
#ifndef MTLPLYLOADER_H
|
||||
#define MTLPLYLOADER_H
|
||||
|
||||
#include "MTLtexture.hpp"
|
||||
|
||||
|
||||
bool loadPLY_MTL(
|
||||
const char * path,
|
||||
std::vector<std::vector<glm::vec3>> & out_vertices,
|
||||
std::vector<std::vector<glm::vec2>> & out_uvs,
|
||||
std::vector<std::vector<glm::vec3>> & out_normals,
|
||||
std::vector<glm::vec3> & out_centers,
|
||||
//std::vector<int> & out_material_name,
|
||||
std::vector<int> & out_material_id,
|
||||
std::string & out_mtllib,
|
||||
int & num_vertices
|
||||
);
|
||||
|
||||
bool loadJSONtextures (
|
||||
std::string jsonpath,
|
||||
std::vector<int> & out_label_id,
|
||||
std::vector<int> & out_segment_id,
|
||||
std::vector<std::vector<int>> & out_face_indices
|
||||
);
|
||||
|
||||
#endif
|
|
@ -1,513 +0,0 @@
|
|||
#include <fstream>
|
||||
//#include <FreeImagePlus.h>
|
||||
#include <GL/glew.h>
|
||||
#include <glfw3.h>
|
||||
#include "common/MTLtexture.hpp"
|
||||
#include <algorithm>
|
||||
|
||||
|
||||
/* parse MTL file */
|
||||
bool parseMTL(std::string mtlpath, std::vector<Material> & out_material){
|
||||
const char* texturePath = mtlpath.c_str();
|
||||
std::ifstream inFile;
|
||||
printf("Parsing %s file for material textures.\n", texturePath);
|
||||
|
||||
/* try to open the file */
|
||||
inFile.open(texturePath);
|
||||
if (!inFile) {
|
||||
printf("%s could not be opened. Are you in the right directory ? Don't forget to read the FAQ !\n", texturePath); getchar();
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* verify the type of file */
|
||||
const char* extension;
|
||||
size_t i = mtlpath.rfind('.', mtlpath.length());
|
||||
if (i != std::string::npos) {
|
||||
extension = mtlpath.substr(i+1, mtlpath.length() - i).c_str();
|
||||
}
|
||||
if (strncmp(extension, "mtl ", 3) != 0) {
|
||||
printf("The file is not an .mtl (%s)\n", texturePath);
|
||||
inFile.close();
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*read file line by line and extract materials and properties*/
|
||||
std::vector<Material> LoadedMaterials;
|
||||
// Go through each line looking for material variables
|
||||
Material tempMaterial;
|
||||
bool listening = false;
|
||||
std::string curline;
|
||||
while (std::getline(inFile, curline)) {
|
||||
// new material and material name
|
||||
if (algorithm::firstToken(curline) == "newmtl") {
|
||||
if (!listening) {
|
||||
listening = true;
|
||||
if (curline.size() > 7) {
|
||||
tempMaterial.name = algorithm::tail(curline);
|
||||
}
|
||||
else {
|
||||
tempMaterial.name = "none";
|
||||
}
|
||||
}
|
||||
else {
|
||||
// Generate the material
|
||||
// Push Back loaded Material
|
||||
|
||||
/*
|
||||
//Debug
|
||||
printf("Temp name: %s\n", tempMaterial.name.c_str());
|
||||
printf("Temp Ka: %i %i %i\n", (int)tempMaterial.Ka.X, (int)tempMaterial.Ka.Y, (int)tempMaterial.Ka.Z);
|
||||
printf("Temp Kd: %i %i %i\n", (int)tempMaterial.Ks.X, (int)tempMaterial.Ks.Y, (int)tempMaterial.Ks.Z);
|
||||
printf("Temp Ks: %i %i %i\n", (int)tempMaterial.Kd.X, (int)tempMaterial.Kd.Y, (int)tempMaterial.Kd.Z);
|
||||
printf("Temp map_Ka: %s\n", tempMaterial.map_Ka.c_str());
|
||||
printf("\n");
|
||||
*/
|
||||
|
||||
out_material.push_back(tempMaterial);
|
||||
// Clear Loaded Material
|
||||
tempMaterial = Material();
|
||||
if (curline.size() > 7) {
|
||||
tempMaterial.name = algorithm::tail(curline);
|
||||
}
|
||||
else {
|
||||
tempMaterial.name = "none";
|
||||
}
|
||||
}
|
||||
}
|
||||
// Ambient Color
|
||||
if (algorithm::firstToken(curline) == "Ka") {
|
||||
std::vector<std::string> temp;
|
||||
algorithm::split(algorithm::tail(curline), temp, " ");
|
||||
if (temp.size() != 3) { continue; }
|
||||
tempMaterial.Ka.X = std::stof(temp[0]);
|
||||
tempMaterial.Ka.Y = std::stof(temp[1]);
|
||||
tempMaterial.Ka.Z = std::stof(temp[2]);
|
||||
}
|
||||
// Diffuse Color
|
||||
if (algorithm::firstToken(curline) == "Kd") {
|
||||
std::vector<std::string> temp;
|
||||
algorithm::split(algorithm::tail(curline), temp, " ");
|
||||
if (temp.size() != 3) { continue; }
|
||||
tempMaterial.Kd.X = std::stof(temp[0]);
|
||||
tempMaterial.Kd.Y = std::stof(temp[1]);
|
||||
tempMaterial.Kd.Z = std::stof(temp[2]);
|
||||
}
|
||||
// Specular Color
|
||||
if (algorithm::firstToken(curline) == "Ks") {
|
||||
std::vector<std::string> temp;
|
||||
algorithm::split(algorithm::tail(curline), temp, " ");
|
||||
if (temp.size() != 3) { continue; }
|
||||
tempMaterial.Ks.X = std::stof(temp[0]);
|
||||
tempMaterial.Ks.Y = std::stof(temp[1]);
|
||||
tempMaterial.Ks.Z = std::stof(temp[2]);
|
||||
}
|
||||
//
|
||||
if (algorithm::firstToken(curline) == "Ke") {
|
||||
std::vector<std::string> temp;
|
||||
algorithm::split(algorithm::tail(curline), temp, " ");
|
||||
if (temp.size() != 3) { continue; }
|
||||
tempMaterial.Ke.X = std::stof(temp[0]);
|
||||
tempMaterial.Ke.Y = std::stof(temp[1]);
|
||||
tempMaterial.Ke.Z = std::stof(temp[2]);
|
||||
}
|
||||
// Specular Exponent
|
||||
if (algorithm::firstToken(curline) == "Ns") {
|
||||
tempMaterial.Ns = std::stof(algorithm::tail(curline));
|
||||
}
|
||||
// Optical Density
|
||||
if (algorithm::firstToken(curline) == "Ni") {
|
||||
tempMaterial.Ni = std::stof(algorithm::tail(curline));
|
||||
}
|
||||
// Dissolve
|
||||
if (algorithm::firstToken(curline) == "d") {
|
||||
tempMaterial.d = std::stof(algorithm::tail(curline));
|
||||
}
|
||||
// Illumination
|
||||
if (algorithm::firstToken(curline) == "illum") {
|
||||
tempMaterial.illum = std::stoi(algorithm::tail(curline));
|
||||
}
|
||||
// Ambient Texture Map
|
||||
if (algorithm::firstToken(curline) == "map_Ka") {
|
||||
tempMaterial.map_Ka = algorithm::tail(curline);
|
||||
}
|
||||
// Diffuse Texture Map
|
||||
if (algorithm::firstToken(curline) == "map_Kd") {
|
||||
tempMaterial.map_Kd = algorithm::tail(curline);
|
||||
}
|
||||
// Specular Texture Map
|
||||
if (algorithm::firstToken(curline) == "map_Ks") {
|
||||
tempMaterial.map_Ks = algorithm::tail(curline);
|
||||
}
|
||||
// Specular Hightlight Map
|
||||
if (algorithm::firstToken(curline) == "map_Ns") {
|
||||
tempMaterial.map_Ns = algorithm::tail(curline);
|
||||
}
|
||||
// Alpha Texture Map
|
||||
if (algorithm::firstToken(curline) == "map_d") {
|
||||
tempMaterial.map_d = algorithm::tail(curline);
|
||||
}
|
||||
// Bump Map
|
||||
if (algorithm::firstToken(curline) == "map_Bump" || algorithm::firstToken(curline) == "map_bump" || algorithm::firstToken(curline) == "bump") {
|
||||
tempMaterial.map_bump = algorithm::tail(curline);
|
||||
}
|
||||
}
|
||||
|
||||
// Deal with last material
|
||||
// Push Back loaded Material
|
||||
out_material.push_back(tempMaterial);
|
||||
|
||||
// Test to see if anything was loaded
|
||||
// If not return false
|
||||
if (out_material.empty()) {
|
||||
printf("The %s file gave no materials back.\n", texturePath); getchar();
|
||||
return 0;
|
||||
}
|
||||
else {
|
||||
printf("Number of loaded materials: %i\n", (int)out_material.size());
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
/* Method to load an image into a texture using the freeimageplus library. */
|
||||
/* Returns the texture ID or dies trying */
|
||||
/* code from: https://r3dux.org/2014/10/how-to-load-an-opengl-texture-using-the-freeimage-library-or-freeimageplus-technically/ */
|
||||
/* Vrtx variable is only used when saving the images (debugging) */
|
||||
/*
|
||||
GLuint loadTextureImages(std::string texturePathString, int Vrtx, GLenum minificationFilter, GLenum magnificationFilter)
|
||||
{
|
||||
|
||||
// Get the texturePath as a pointer to a const char array to play nice with FreeImage
|
||||
const char* texturePath = texturePathString.c_str();
|
||||
|
||||
// Determine the format of the image.
|
||||
// Note: The second paramter ('size') is currently unused, and we should use 0 for it.
|
||||
FREE_IMAGE_FORMAT format = FreeImage_GetFileType(texturePath , 0);
|
||||
|
||||
// Image not found? Abort! Without this section we get a 0 by 0 image with 0 bits-per-pixel but we don't abort, which
|
||||
// you might find preferable to dumping the user back to the desktop.
|
||||
if (format == -1)
|
||||
{
|
||||
printf("Could not find image: %s - Aborting.\n", texturePath);
|
||||
exit(-1);
|
||||
}
|
||||
|
||||
// Found image, but couldn't determine the file format? Try again...
|
||||
if (format == FIF_UNKNOWN)
|
||||
{
|
||||
printf("Couldn't determine file format - attempting to get from file extension...\n");
|
||||
|
||||
// ...by getting the filetype from the texturePath extension (i.e. .PNG, .GIF etc.)
|
||||
// Note: This is slower and more error-prone that getting it from the file itself,
|
||||
// also, we can't use the 'U' (unicode) variant of this method as that's Windows only.
|
||||
format = FreeImage_GetFIFFromFilename(texturePath);
|
||||
|
||||
// Check that the plugin has reading capabilities for this format (if it's FIF_UNKNOWN,
|
||||
// for example, then it won't have) - if we can't read the file, then we bail out =(
|
||||
if ( !FreeImage_FIFSupportsReading(format) )
|
||||
{
|
||||
printf("Detected image format cannot be read!\n");
|
||||
exit(-1);
|
||||
}
|
||||
}
|
||||
|
||||
// If we're here we have a known image format, so load the image into a bitap
|
||||
FIBITMAP* bitmap = FreeImage_Load(format, texturePath);
|
||||
|
||||
// How many bits-per-pixel is the source image?
|
||||
int bitsPerPixel = FreeImage_GetBPP(bitmap);
|
||||
|
||||
|
||||
// Convert our image up to 32 bits (8 bits per channel, Red/Green/Blue/Alpha) -
|
||||
// but only if the image is not already 32 bits (i.e. 8 bits per channel).
|
||||
// Note: ConvertTo32Bits returns a CLONE of the image data - so if we
|
||||
// allocate this back to itself without using our bitmap32 intermediate
|
||||
// we will LEAK the original bitmap data, and valgrind will show things like this:
|
||||
//
|
||||
// LEAK SUMMARY:
|
||||
// definitely lost: 24 bytes in 2 blocks
|
||||
// indirectly lost: 1,024,874 bytes in 14 blocks <--- Ouch.
|
||||
//
|
||||
// Using our intermediate and cleaning up the initial bitmap data we get:
|
||||
//
|
||||
// LEAK SUMMARY:
|
||||
// definitely lost: 16 bytes in 1 blocks
|
||||
// indirectly lost: 176 bytes in 4 blocks
|
||||
//
|
||||
// All above leaks (192 bytes) are caused by XGetDefault (in /usr/lib/libX11.so.6.3.0) - we have no control over this.
|
||||
//
|
||||
FIBITMAP* bitmap32;
|
||||
if (bitsPerPixel == 32)
|
||||
{
|
||||
//printf("Source image has %i bits per pixel. Skipping conversion.\n", bitsPerPixel); //debug
|
||||
bitmap32 = bitmap;
|
||||
}
|
||||
else
|
||||
{
|
||||
//printf("Source image has %i bits per pixel. Converting to 32-bit color.\n", bitsPerPixel); //debug
|
||||
bitmap32 = FreeImage_ConvertTo32Bits(bitmap);
|
||||
}
|
||||
|
||||
// Some basic image info - strip it out if you don't care
|
||||
int imageWidth = FreeImage_GetWidth(bitmap32);
|
||||
int imageHeight = FreeImage_GetHeight(bitmap32);
|
||||
//printf("Image: %s is of size: %i x %i.\n", texturePath, imageWidth, imageHeight); //debug
|
||||
|
||||
// Debug Image colorization
|
||||
std::string path = "/root/mount/gibson/FreeImageTexture_" + std::to_string(Vrtx) + ".png";
|
||||
if (FreeImage_Save( FIF_PNG , bitmap32 , path.c_str() , 0 )) {
|
||||
printf("Saved image succesfully!\n");
|
||||
}
|
||||
|
||||
|
||||
// Get a pointer to the texture data as an array of unsigned bytes.
|
||||
// Note: At this point bitmap32 ALWAYS holds a 32-bit colour version of our image - so we get our data from that.
|
||||
// Also, we don't need to delete or delete[] this textureData because it's not on the heap (so attempting to do
|
||||
// so will cause a crash) - just let it go out of scope and the memory will be returned to the stack.
|
||||
GLubyte* textureData = FreeImage_GetBits(bitmap32);
|
||||
|
||||
// Generate a texture ID and bind to it
|
||||
GLuint tempTextureID;
|
||||
glGenTextures(1, &tempTextureID);
|
||||
glBindTexture(GL_TEXTURE_2D, tempTextureID);
|
||||
|
||||
// Construct the texture.
|
||||
// Note: The 'Data format' is the format of the image data as provided by the image library. FreeImage decodes images into
|
||||
// BGR/BGRA format, but we want to work with it in the more common RGBA format, so we specify the 'Internal format' as such.
|
||||
glTexImage2D(GL_TEXTURE_2D, // Type of texture
|
||||
0, // Mipmap level (0 being the top level i.e. full size)
|
||||
GL_RGBA, // Internal format
|
||||
imageWidth, // Width of the texture
|
||||
imageHeight, // Height of the texture,
|
||||
0, // Border in pixels
|
||||
GL_BGRA, // Data format
|
||||
GL_UNSIGNED_BYTE, // Type of texture data
|
||||
textureData); // The image data to use for this texture
|
||||
|
||||
// Specify our minification and magnification filters
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, minificationFilter);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, magnificationFilter);
|
||||
|
||||
// If we're using MipMaps, then we'll generate them here.
|
||||
// Note: The glGenerateMipmap call requires OpenGL 3.0 as a minimum.
|
||||
if (minificationFilter == GL_LINEAR_MIPMAP_LINEAR ||
|
||||
minificationFilter == GL_LINEAR_MIPMAP_NEAREST ||
|
||||
minificationFilter == GL_NEAREST_MIPMAP_LINEAR ||
|
||||
minificationFilter == GL_NEAREST_MIPMAP_NEAREST)
|
||||
{
|
||||
glGenerateMipmap(GL_TEXTURE_2D);
|
||||
}
|
||||
|
||||
// Check for OpenGL texture creation errors
|
||||
GLenum glError = glGetError();
|
||||
if(glError)
|
||||
{
|
||||
printf("There was an error loading the texture: %s\n", texturePath);
|
||||
|
||||
switch (glError)
|
||||
{
|
||||
case GL_INVALID_ENUM:
|
||||
printf("Invalid enum.\n");
|
||||
break;
|
||||
|
||||
case GL_INVALID_VALUE:
|
||||
printf("Invalid value.\n");
|
||||
break;
|
||||
|
||||
case GL_INVALID_OPERATION:
|
||||
printf("Invalid operation.\n");
|
||||
|
||||
default:
|
||||
printf("Unrecognised GLenum.\n");
|
||||
break;
|
||||
}
|
||||
|
||||
printf("See https://www.opengl.org/sdk/docs/man/html/glTexImage2D.xhtml for further details.\n");
|
||||
}
|
||||
|
||||
// Unload the 32-bit colour bitmap
|
||||
FreeImage_Unload(bitmap32);
|
||||
|
||||
// If we had to do a conversion to 32-bit colour, then unload the original
|
||||
// non-32-bit-colour version of the image data too. Otherwise, bitmap32 and
|
||||
// bitmap point at the same data, and that data's already been free'd, so
|
||||
// don't attempt to free it again! (or we'll crash).
|
||||
if (bitsPerPixel != 32)
|
||||
{
|
||||
FreeImage_Unload(bitmap);
|
||||
}
|
||||
|
||||
// Finally, return the texture ID
|
||||
return tempTextureID;
|
||||
}
|
||||
*/
|
||||
|
||||
/* Generate images of solid color and assign them to textures */
|
||||
/* For mtl files with no associated maps (textureimages) */
|
||||
/* Vrtx variable is only used when saving the images (debugging) */
|
||||
/*GLuint solidColorTexture(Vector3 Ka, int texLevel, GLenum minificationFilter, GLenum magnificationFilter) {
|
||||
int imageWidth = 100;
|
||||
int imageHeight = 100;
|
||||
FIBITMAP* bitmap32 = FreeImage_Allocate(imageWidth, imageHeight, 32);
|
||||
if (!bitmap32) {
|
||||
printf("You can't allocate the texture image.\n");
|
||||
exit(-1);
|
||||
}
|
||||
unsigned char color[4] = {static_cast<unsigned char>(((unsigned int)Ka.X >> 24)*255),
|
||||
static_cast<unsigned char>(((unsigned int)Ka.Y >> 24)*255),
|
||||
static_cast<unsigned char>(((unsigned int)Ka.Z >> 24)*255), 255};
|
||||
FreeImage_FillBackground(bitmap32, color);
|
||||
|
||||
// Debug Image colorization
|
||||
std::string path = "/root/mount/gibson/FreeImageTexture_" + std::to_string(Vrtx) + ".png";
|
||||
if (FreeImage_Save( FIF_PNG , bitmap32 , path.c_str() , 0 )) {
|
||||
printf("Saved image succesfully!\n");
|
||||
}
|
||||
|
||||
|
||||
// Assign texture to OpenGL
|
||||
GLubyte* textureData = FreeImage_GetBits(bitmap32);
|
||||
|
||||
|
||||
// Generate a texture ID and bind to it
|
||||
GLuint tempTextureID;
|
||||
glGenTextures(1, &tempTextureID);
|
||||
glBindTexture(GL_TEXTURE_2D, tempTextureID);
|
||||
|
||||
// Construct the texture.
|
||||
// Note: The 'Data format' is the format of the image data as provided by the image library. FreeImage decodes images into
|
||||
// BGR/BGRA format, but we want to work with it in the more common RGBA format, so we specify the 'Internal format' as such.
|
||||
glTexImage2D(GL_TEXTURE_2D, // Type of texture
|
||||
texLevel, // Mipmap level (0 being the top level i.e. full size)
|
||||
GL_RGBA, // Internal format
|
||||
imageWidth, // Width of the texture
|
||||
imageHeight, // Height of the texture,
|
||||
0, // Border in pixels
|
||||
GL_BGRA, // Data format
|
||||
GL_UNSIGNED_BYTE, // Type of texture data
|
||||
textureData); // The image data to use for this texture
|
||||
|
||||
// Specify our minification and magnification filters
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, minificationFilter);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, magnificationFilter);
|
||||
|
||||
// If we're using MipMaps, then we'll generate them here.
|
||||
// Note: The glGenerateMipmap call requires OpenGL 3.0 as a minimum.
|
||||
if (minificationFilter == GL_LINEAR_MIPMAP_LINEAR ||
|
||||
minificationFilter == GL_LINEAR_MIPMAP_NEAREST ||
|
||||
minificationFilter == GL_NEAREST_MIPMAP_LINEAR ||
|
||||
minificationFilter == GL_NEAREST_MIPMAP_NEAREST)
|
||||
{
|
||||
glGenerateMipmap(GL_TEXTURE_2D);
|
||||
}
|
||||
|
||||
|
||||
//return tempTextureID;
|
||||
return 0;
|
||||
}*/
|
||||
|
||||
#include <sstream>
|
||||
/* main function to parse MTL files, load or generate texture iamges and generate openGL texture IDs */
|
||||
bool loadMTLtextures (std::string mtlpath, std::vector<TextureObj> & objText, std::vector<std::string> OBJmaterial_name) {
|
||||
std::vector<Material> parsed_mtl_file;
|
||||
if (parseMTL(mtlpath, parsed_mtl_file) == 0){
|
||||
printf("The Material list is empty! Nothing more to process.\n"); getchar();
|
||||
return 0;
|
||||
}
|
||||
|
||||
// ----- Initialise the FreeImage library -----
|
||||
// Note: Flag is whether we should load ONLY local (built-in) libraries, so
|
||||
// false means 'no, use external libraries also', and 'true' means - use built
|
||||
// in libs only, so it's like using the library as a static version of itself.
|
||||
//FreeImage_Initialise(true);
|
||||
std::string imagePath;
|
||||
// load texture images only if they exist, or assign standard color
|
||||
for ( unsigned int i = 0; i < parsed_mtl_file.size(); i++) {
|
||||
// check if material exists in the obj file and keep only these materials
|
||||
if (std::find(OBJmaterial_name.begin(), OBJmaterial_name.end(), parsed_mtl_file[i].name) != OBJmaterial_name.end()) {
|
||||
if (!parsed_mtl_file[i].map_Ka.empty() || !parsed_mtl_file[i].map_Kd.empty() || !parsed_mtl_file[i].map_Ks.empty()) {
|
||||
printf("Reading Texture Images for textures.\n"); //debug
|
||||
if (!parsed_mtl_file[i].map_Ka.empty()) {
|
||||
imagePath = parsed_mtl_file[i].map_Ka;
|
||||
}
|
||||
else if (!parsed_mtl_file[i].map_Kd.empty()) {
|
||||
imagePath = parsed_mtl_file[i].map_Kd;
|
||||
}
|
||||
else if (!parsed_mtl_file[i].map_Ks.empty()) {
|
||||
imagePath = parsed_mtl_file[i].map_Ks;
|
||||
}
|
||||
else {
|
||||
printf("Could not find any image path.\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
std::string texturePath;
|
||||
std::string rgbString = "rgb.mtl";
|
||||
std::string semanticString = "semantic.mtl";
|
||||
if (mtlpath.find(rgbString) != std::string::npos) {
|
||||
texturePath.append(mtlpath.c_str(), mtlpath.length() - rgbString.length());
|
||||
texturePath.append(imagePath);
|
||||
}
|
||||
else if (mtlpath.find(semanticString) != std::string::npos) {
|
||||
texturePath.append(mtlpath.c_str(), mtlpath.length() - semanticString.length());
|
||||
texturePath.append(imagePath);
|
||||
}
|
||||
else {
|
||||
printf("Could not find folder path to the image.\n");
|
||||
return 0;
|
||||
}*/
|
||||
|
||||
TextureObj tempText;
|
||||
tempText.name = parsed_mtl_file[i].name;
|
||||
// Load an image and bind it to a texture
|
||||
// TODO (hzyjerry): 2D3DS mtl image problem
|
||||
tempText.textureID = i;//loadTextureImages(texturePath, i);
|
||||
objText.push_back(tempText);
|
||||
}
|
||||
if (parsed_mtl_file[i].map_Ka.empty() || parsed_mtl_file[i].map_Kd.empty() || parsed_mtl_file[i].map_Ks.empty()) {
|
||||
//printf("Generating Texture Images for textures (no texture images exist).\n"); //debug
|
||||
// Create a handle for our texture
|
||||
GLuint tempTextureID;
|
||||
TextureObj tempText;
|
||||
tempText.name = parsed_mtl_file[i].name;
|
||||
//printf("material name to generate image: %s\n", tempText.name.c_str()); //debug
|
||||
|
||||
// Generate an image of solid texture and bind it to texture
|
||||
// TODO (hzyjerry): 2D3DS mtl image problem
|
||||
tempText.textureID = i; //solidColorTexture(parsed_mtl_file[i].Ka, i);
|
||||
objText.push_back(tempText);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (objText.size() != OBJmaterial_name.size()) {
|
||||
printf("Number of materials loaded (%i) is different from number of materials in the OBJ file (%i).\n", (int)objText.size(), (int)OBJmaterial_name.size());
|
||||
return 0;
|
||||
}
|
||||
|
||||
// todo: UV map coordinates howe to add it to the texture map/
|
||||
// maybe not here???
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
|
||||
bool loadPLYtextures(
|
||||
std::vector<TextureObj> & objText,
|
||||
//std::vector<std::string> PLYmaterial_name,
|
||||
std::vector<int> PLYmaterial_id) {
|
||||
|
||||
for (uint i = 0; i < PLYmaterial_id.size(); i++) {
|
||||
TextureObj tempText;
|
||||
//tempText.name = PLYmaterial_name[i];
|
||||
tempText.name = "";
|
||||
// Load an image and bind it to a texture
|
||||
tempText.textureID = PLYmaterial_id[i];
|
||||
objText.push_back(tempText);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
|
@ -1,210 +0,0 @@
|
|||
#ifndef MTLTEXTURE_HPP
|
||||
#define MTLTEXTURE_HPP
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <vector>
|
||||
#include <GL/glut.h>
|
||||
#include <GL/glx.h>
|
||||
|
||||
|
||||
struct Vector3
|
||||
{
|
||||
// Default Constructor
|
||||
Vector3()
|
||||
{
|
||||
X = 0.0f;
|
||||
Y = 0.0f;
|
||||
Z = 0.0f;
|
||||
}
|
||||
// Variable Set Constructor
|
||||
Vector3(float X_, float Y_, float Z_)
|
||||
{
|
||||
X = X_;
|
||||
Y = Y_;
|
||||
Z = Z_;
|
||||
}
|
||||
// Bool Equals Operator Overload
|
||||
bool operator==(const Vector3& other) const
|
||||
{
|
||||
return (this->X == other.X && this->Y == other.Y && this->Z == other.Z);
|
||||
}
|
||||
// Bool Not Equals Operator Overload
|
||||
bool operator!=(const Vector3& other) const
|
||||
{
|
||||
return !(this->X == other.X && this->Y == other.Y && this->Z == other.Z);
|
||||
}
|
||||
// Addition Operator Overload
|
||||
Vector3 operator+(const Vector3& right) const
|
||||
{
|
||||
return Vector3(this->X + right.X, this->Y + right.Y, this->Z + right.Z);
|
||||
}
|
||||
// Subtraction Operator Overload
|
||||
Vector3 operator-(const Vector3& right) const
|
||||
{
|
||||
return Vector3(this->X - right.X, this->Y - right.Y, this->Z - right.Z);
|
||||
}
|
||||
// Float Multiplication Operator Overload
|
||||
Vector3 operator*(const float& other) const
|
||||
{
|
||||
return Vector3(this->X *other, this->Y * other, this->Z - other);
|
||||
}
|
||||
|
||||
// Positional Variables
|
||||
float X;
|
||||
float Y;
|
||||
float Z;
|
||||
};
|
||||
|
||||
struct Material
|
||||
{
|
||||
Material()
|
||||
{
|
||||
name;
|
||||
Ns = 0.0f;
|
||||
Ni = 0.0f;
|
||||
d = 0.0f;
|
||||
illum = 0;
|
||||
}
|
||||
|
||||
std::string name; // Material Name
|
||||
Vector3 Ka; // Ambient Color
|
||||
Vector3 Kd; // Diffuse Color
|
||||
Vector3 Ks; // Specular Color
|
||||
Vector3 Ke;
|
||||
float Ns; // Specular Exponent
|
||||
float Ni; // Optical Density
|
||||
float d; // Dissolve
|
||||
int illum; // Illumination
|
||||
std::string map_Ka; // Ambient Texture Map
|
||||
std::string map_Kd; // Diffuse Texture Map
|
||||
std::string map_Ks; // Specular Texture Map
|
||||
std::string map_Ns; // Specular Hightlight Map
|
||||
std::string map_d; // Alpha Texture Map
|
||||
std::string map_bump; // Bump Map
|
||||
};
|
||||
|
||||
struct TextureObj
|
||||
{
|
||||
TextureObj()
|
||||
{
|
||||
name;
|
||||
textureID;
|
||||
}
|
||||
std::string name;
|
||||
GLuint textureID;
|
||||
};
|
||||
|
||||
|
||||
namespace algorithm {
|
||||
// Split a String into a string array at a given token
|
||||
inline void split(const std::string &in,
|
||||
std::vector<std::string> &out,
|
||||
std::string token)
|
||||
{
|
||||
out.clear();
|
||||
|
||||
std::string temp;
|
||||
|
||||
for (int i = 0; i < int(in.size()); i++)
|
||||
{
|
||||
std::string test = in.substr(i, token.size());
|
||||
|
||||
if (test == token)
|
||||
{
|
||||
if (!temp.empty())
|
||||
{
|
||||
out.push_back(temp);
|
||||
temp.clear();
|
||||
i += (int)token.size() - 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
out.push_back("");
|
||||
}
|
||||
}
|
||||
else if (i + token.size() >= in.size())
|
||||
{
|
||||
temp += in.substr(i, token.size());
|
||||
out.push_back(temp);
|
||||
break;
|
||||
}
|
||||
else
|
||||
{
|
||||
temp += in[i];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Get tail of string after first token and possibly following spaces
|
||||
inline std::string tail(const std::string &in)
|
||||
{
|
||||
size_t token_start = in.find_first_not_of(" \t");
|
||||
size_t space_start = in.find_first_of(" \t", token_start);
|
||||
size_t tail_start = in.find_first_not_of(" \t", space_start);
|
||||
size_t tail_end = in.find_last_not_of(" \t");
|
||||
if (tail_start != std::string::npos && tail_end != std::string::npos)
|
||||
{
|
||||
return in.substr(tail_start, tail_end - tail_start + 1);
|
||||
}
|
||||
else if (tail_start != std::string::npos)
|
||||
{
|
||||
return in.substr(tail_start);
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
// Get first token of string
|
||||
inline std::string firstToken(const std::string &in)
|
||||
{
|
||||
if (!in.empty())
|
||||
{
|
||||
size_t token_start = in.find_first_not_of(" \t");
|
||||
size_t token_end = in.find_first_of(" \t", token_start);
|
||||
if (token_start != std::string::npos && token_end != std::string::npos)
|
||||
{
|
||||
return in.substr(token_start, token_end - token_start);
|
||||
}
|
||||
else if (token_start != std::string::npos)
|
||||
{
|
||||
return in.substr(token_start);
|
||||
}
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
// Get element at given index position
|
||||
template <class T>
|
||||
inline const T & getElement(const std::vector<T> &elements, std::string &index)
|
||||
{
|
||||
int idx = std::stoi(index);
|
||||
if (idx < 0)
|
||||
idx = int(elements.size()) + idx;
|
||||
else
|
||||
idx--;
|
||||
return elements[idx];
|
||||
}
|
||||
}
|
||||
|
||||
/* parse MTL file */
|
||||
bool parseMTL(std::string mtlpath, std::vector<Material> & out_material);
|
||||
|
||||
/* Method to load an image into a texture using the freeimageplus library. */
|
||||
/* Returns the texture ID or dies trying */
|
||||
/* code from: https://r3dux.org/2014/10/how-to-load-an-opengl-texture-using-the-freeimage-library-or-freeimageplus-technically/ */
|
||||
//GLuint loadTextureImages(std::string texturePathString, int Vrtx, GLenum minificationFilter = GL_LINEAR, GLenum magnificationFilter = GL_LINEAR);
|
||||
|
||||
/* Generate images of solid color and assign them to textures */
|
||||
/* For mtl files with no associated maps (textureimages) */
|
||||
//GLuint solidColorTexture(Vector3 Ka, int Vrtx, GLenum minificationFilter = GL_LINEAR, GLenum magnificationFilter = GL_LINEAR);
|
||||
|
||||
/* main function to parse MTL files, load or generate texture iamges and generate openGL texture IDs */
|
||||
bool loadMTLtextures (std::string mtlpath, std::vector<TextureObj> & objtext, std::vector<std::string> OBJMaterial_name);
|
||||
|
||||
|
||||
bool loadPLYtextures(std::vector<TextureObj> & objText,
|
||||
//std::vector<std::string> PLYmaterial_name,
|
||||
std::vector<int> PLYmaterial_id);
|
||||
|
||||
#endif
|
|
@ -1,809 +0,0 @@
|
|||
/*
|
||||
Copyright (c) 2009, Hideyuki Tanaka
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are met:
|
||||
* Redistributions of source code must retain the above copyright
|
||||
notice, this list of conditions and the following disclaimer.
|
||||
* Redistributions in binary form must reproduce the above copyright
|
||||
notice, this list of conditions and the following disclaimer in the
|
||||
documentation and/or other materials provided with the distribution.
|
||||
* Neither the name of the <organization> nor the
|
||||
names of its contributors may be used to endorse or promote products
|
||||
derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY <copyright holder> ''AS IS'' AND ANY
|
||||
EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL <copyright holder> BE LIABLE FOR ANY
|
||||
DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
|
||||
ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <iostream>
|
||||
#include <sstream>
|
||||
#include <vector>
|
||||
#include <map>
|
||||
#include <string>
|
||||
#include <stdexcept>
|
||||
#include <typeinfo>
|
||||
#include <cstring>
|
||||
#include <algorithm>
|
||||
#include <cxxabi.h>
|
||||
#include <cstdlib>
|
||||
|
||||
namespace cmdline{
|
||||
|
||||
namespace detail{
|
||||
|
||||
template <typename Target, typename Source, bool Same>
|
||||
class lexical_cast_t{
|
||||
public:
|
||||
static Target cast(const Source &arg){
|
||||
Target ret;
|
||||
std::stringstream ss;
|
||||
if (!(ss<<arg && ss>>ret && ss.eof()))
|
||||
throw std::bad_cast();
|
||||
|
||||
return ret;
|
||||
}
|
||||
};
|
||||
|
||||
template <typename Target, typename Source>
|
||||
class lexical_cast_t<Target, Source, true>{
|
||||
public:
|
||||
static Target cast(const Source &arg){
|
||||
return arg;
|
||||
}
|
||||
};
|
||||
|
||||
template <typename Source>
|
||||
class lexical_cast_t<std::string, Source, false>{
|
||||
public:
|
||||
static std::string cast(const Source &arg){
|
||||
std::ostringstream ss;
|
||||
ss<<arg;
|
||||
return ss.str();
|
||||
}
|
||||
};
|
||||
|
||||
template <typename Target>
|
||||
class lexical_cast_t<Target, std::string, false>{
|
||||
public:
|
||||
static Target cast(const std::string &arg){
|
||||
Target ret;
|
||||
std::istringstream ss(arg);
|
||||
if (!(ss>>ret && ss.eof()))
|
||||
throw std::bad_cast();
|
||||
return ret;
|
||||
}
|
||||
};
|
||||
|
||||
template <typename T1, typename T2>
|
||||
struct is_same {
|
||||
static const bool value = false;
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
struct is_same<T, T>{
|
||||
static const bool value = true;
|
||||
};
|
||||
|
||||
template<typename Target, typename Source>
|
||||
Target lexical_cast(const Source &arg)
|
||||
{
|
||||
return lexical_cast_t<Target, Source, detail::is_same<Target, Source>::value>::cast(arg);
|
||||
}
|
||||
|
||||
static inline std::string demangle(const std::string &name)
|
||||
{
|
||||
int status=0;
|
||||
char *p=abi::__cxa_demangle(name.c_str(), 0, 0, &status);
|
||||
std::string ret(p);
|
||||
free(p);
|
||||
return ret;
|
||||
}
|
||||
|
||||
template <class T>
|
||||
std::string readable_typename()
|
||||
{
|
||||
return demangle(typeid(T).name());
|
||||
}
|
||||
|
||||
template <class T>
|
||||
std::string default_value(T def)
|
||||
{
|
||||
return detail::lexical_cast<std::string>(def);
|
||||
}
|
||||
|
||||
template <>
|
||||
inline std::string readable_typename<std::string>()
|
||||
{
|
||||
return "string";
|
||||
}
|
||||
|
||||
} // detail
|
||||
|
||||
//-----
|
||||
|
||||
class cmdline_error : public std::exception {
|
||||
public:
|
||||
cmdline_error(const std::string &msg): msg(msg){}
|
||||
~cmdline_error() throw() {}
|
||||
const char *what() const throw() { return msg.c_str(); }
|
||||
private:
|
||||
std::string msg;
|
||||
};
|
||||
|
||||
template <class T>
|
||||
struct default_reader{
|
||||
T operator()(const std::string &str){
|
||||
return detail::lexical_cast<T>(str);
|
||||
}
|
||||
};
|
||||
|
||||
template <class T>
|
||||
struct range_reader{
|
||||
range_reader(const T &low, const T &high): low(low), high(high) {}
|
||||
T operator()(const std::string &s) const {
|
||||
T ret=default_reader<T>()(s);
|
||||
if (!(ret>=low && ret<=high)) throw cmdline::cmdline_error("range_error");
|
||||
return ret;
|
||||
}
|
||||
private:
|
||||
T low, high;
|
||||
};
|
||||
|
||||
template <class T>
|
||||
range_reader<T> range(const T &low, const T &high)
|
||||
{
|
||||
return range_reader<T>(low, high);
|
||||
}
|
||||
|
||||
template <class T>
|
||||
struct oneof_reader{
|
||||
T operator()(const std::string &s){
|
||||
T ret=default_reader<T>()(s);
|
||||
if (std::find(alt.begin(), alt.end(), ret)==alt.end())
|
||||
throw cmdline_error("");
|
||||
return ret;
|
||||
}
|
||||
void add(const T &v){ alt.push_back(v); }
|
||||
private:
|
||||
std::vector<T> alt;
|
||||
};
|
||||
|
||||
template <class T>
|
||||
oneof_reader<T> oneof(T a1)
|
||||
{
|
||||
oneof_reader<T> ret;
|
||||
ret.add(a1);
|
||||
return ret;
|
||||
}
|
||||
|
||||
template <class T>
|
||||
oneof_reader<T> oneof(T a1, T a2)
|
||||
{
|
||||
oneof_reader<T> ret;
|
||||
ret.add(a1);
|
||||
ret.add(a2);
|
||||
return ret;
|
||||
}
|
||||
|
||||
template <class T>
|
||||
oneof_reader<T> oneof(T a1, T a2, T a3)
|
||||
{
|
||||
oneof_reader<T> ret;
|
||||
ret.add(a1);
|
||||
ret.add(a2);
|
||||
ret.add(a3);
|
||||
return ret;
|
||||
}
|
||||
|
||||
template <class T>
|
||||
oneof_reader<T> oneof(T a1, T a2, T a3, T a4)
|
||||
{
|
||||
oneof_reader<T> ret;
|
||||
ret.add(a1);
|
||||
ret.add(a2);
|
||||
ret.add(a3);
|
||||
ret.add(a4);
|
||||
return ret;
|
||||
}
|
||||
|
||||
template <class T>
|
||||
oneof_reader<T> oneof(T a1, T a2, T a3, T a4, T a5)
|
||||
{
|
||||
oneof_reader<T> ret;
|
||||
ret.add(a1);
|
||||
ret.add(a2);
|
||||
ret.add(a3);
|
||||
ret.add(a4);
|
||||
ret.add(a5);
|
||||
return ret;
|
||||
}
|
||||
|
||||
template <class T>
|
||||
oneof_reader<T> oneof(T a1, T a2, T a3, T a4, T a5, T a6)
|
||||
{
|
||||
oneof_reader<T> ret;
|
||||
ret.add(a1);
|
||||
ret.add(a2);
|
||||
ret.add(a3);
|
||||
ret.add(a4);
|
||||
ret.add(a5);
|
||||
ret.add(a6);
|
||||
return ret;
|
||||
}
|
||||
|
||||
template <class T>
|
||||
oneof_reader<T> oneof(T a1, T a2, T a3, T a4, T a5, T a6, T a7)
|
||||
{
|
||||
oneof_reader<T> ret;
|
||||
ret.add(a1);
|
||||
ret.add(a2);
|
||||
ret.add(a3);
|
||||
ret.add(a4);
|
||||
ret.add(a5);
|
||||
ret.add(a6);
|
||||
ret.add(a7);
|
||||
return ret;
|
||||
}
|
||||
|
||||
template <class T>
|
||||
oneof_reader<T> oneof(T a1, T a2, T a3, T a4, T a5, T a6, T a7, T a8)
|
||||
{
|
||||
oneof_reader<T> ret;
|
||||
ret.add(a1);
|
||||
ret.add(a2);
|
||||
ret.add(a3);
|
||||
ret.add(a4);
|
||||
ret.add(a5);
|
||||
ret.add(a6);
|
||||
ret.add(a7);
|
||||
ret.add(a8);
|
||||
return ret;
|
||||
}
|
||||
|
||||
template <class T>
|
||||
oneof_reader<T> oneof(T a1, T a2, T a3, T a4, T a5, T a6, T a7, T a8, T a9)
|
||||
{
|
||||
oneof_reader<T> ret;
|
||||
ret.add(a1);
|
||||
ret.add(a2);
|
||||
ret.add(a3);
|
||||
ret.add(a4);
|
||||
ret.add(a5);
|
||||
ret.add(a6);
|
||||
ret.add(a7);
|
||||
ret.add(a8);
|
||||
ret.add(a9);
|
||||
return ret;
|
||||
}
|
||||
|
||||
template <class T>
|
||||
oneof_reader<T> oneof(T a1, T a2, T a3, T a4, T a5, T a6, T a7, T a8, T a9, T a10)
|
||||
{
|
||||
oneof_reader<T> ret;
|
||||
ret.add(a1);
|
||||
ret.add(a2);
|
||||
ret.add(a3);
|
||||
ret.add(a4);
|
||||
ret.add(a5);
|
||||
ret.add(a6);
|
||||
ret.add(a7);
|
||||
ret.add(a8);
|
||||
ret.add(a9);
|
||||
ret.add(a10);
|
||||
return ret;
|
||||
}
|
||||
|
||||
//-----
|
||||
|
||||
class parser{
|
||||
public:
|
||||
parser(){
|
||||
}
|
||||
~parser(){
|
||||
for (std::map<std::string, option_base*>::iterator p=options.begin();
|
||||
p!=options.end(); p++)
|
||||
delete p->second;
|
||||
}
|
||||
|
||||
void add(const std::string &name,
|
||||
char short_name=0,
|
||||
const std::string &desc=""){
|
||||
if (options.count(name)) throw cmdline_error("multiple definition: "+name);
|
||||
options[name]=new option_without_value(name, short_name, desc);
|
||||
ordered.push_back(options[name]);
|
||||
}
|
||||
|
||||
template <class T>
|
||||
void add(const std::string &name,
|
||||
char short_name=0,
|
||||
const std::string &desc="",
|
||||
bool need=true,
|
||||
const T def=T()){
|
||||
add(name, short_name, desc, need, def, default_reader<T>());
|
||||
}
|
||||
|
||||
template <class T, class F>
|
||||
void add(const std::string &name,
|
||||
char short_name=0,
|
||||
const std::string &desc="",
|
||||
bool need=true,
|
||||
const T def=T(),
|
||||
F reader=F()){
|
||||
if (options.count(name)) throw cmdline_error("multiple definition: "+name);
|
||||
options[name]=new option_with_value_with_reader<T, F>(name, short_name, need, def, desc, reader);
|
||||
ordered.push_back(options[name]);
|
||||
}
|
||||
|
||||
void footer(const std::string &f){
|
||||
ftr=f;
|
||||
}
|
||||
|
||||
void set_program_name(const std::string &name){
|
||||
prog_name=name;
|
||||
}
|
||||
|
||||
bool exist(const std::string &name) const {
|
||||
if (options.count(name)==0) throw cmdline_error("there is no flag: --"+name);
|
||||
return options.find(name)->second->has_set();
|
||||
}
|
||||
|
||||
template <class T>
|
||||
const T &get(const std::string &name) const {
|
||||
if (options.count(name)==0) throw cmdline_error("there is no flag: --"+name);
|
||||
const option_with_value<T> *p=dynamic_cast<const option_with_value<T>*>(options.find(name)->second);
|
||||
if (p==NULL) throw cmdline_error("type mismatch flag '"+name+"'");
|
||||
return p->get();
|
||||
}
|
||||
|
||||
const std::vector<std::string> &rest() const {
|
||||
return others;
|
||||
}
|
||||
|
||||
bool parse(const std::string &arg){
|
||||
std::vector<std::string> args;
|
||||
|
||||
std::string buf;
|
||||
bool in_quote=false;
|
||||
for (std::string::size_type i=0; i<arg.length(); i++){
|
||||
if (arg[i]=='\"'){
|
||||
in_quote=!in_quote;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (arg[i]==' ' && !in_quote){
|
||||
args.push_back(buf);
|
||||
buf="";
|
||||
continue;
|
||||
}
|
||||
|
||||
if (arg[i]=='\\'){
|
||||
i++;
|
||||
if (i>=arg.length()){
|
||||
errors.push_back("unexpected occurrence of '\\' at end of string");
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
buf+=arg[i];
|
||||
}
|
||||
|
||||
if (in_quote){
|
||||
errors.push_back("quote is not closed");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (buf.length()>0)
|
||||
args.push_back(buf);
|
||||
|
||||
for (size_t i=0; i<args.size(); i++)
|
||||
std::cout<<"\""<<args[i]<<"\""<<std::endl;
|
||||
|
||||
return parse(args);
|
||||
}
|
||||
|
||||
bool parse(const std::vector<std::string> &args){
|
||||
int argc=static_cast<int>(args.size());
|
||||
std::vector<const char*> argv(argc);
|
||||
|
||||
for (int i=0; i<argc; i++)
|
||||
argv[i]=args[i].c_str();
|
||||
|
||||
return parse(argc, &argv[0]);
|
||||
}
|
||||
|
||||
bool parse(int argc, const char * const argv[]){
|
||||
errors.clear();
|
||||
others.clear();
|
||||
|
||||
if (argc<1){
|
||||
errors.push_back("argument number must be longer than 0");
|
||||
return false;
|
||||
}
|
||||
if (prog_name=="")
|
||||
prog_name=argv[0];
|
||||
|
||||
std::map<char, std::string> lookup;
|
||||
for (std::map<std::string, option_base*>::iterator p=options.begin();
|
||||
p!=options.end(); p++){
|
||||
if (p->first.length()==0) continue;
|
||||
char initial=p->second->short_name();
|
||||
if (initial){
|
||||
if (lookup.count(initial)>0){
|
||||
lookup[initial]="";
|
||||
errors.push_back(std::string("short option '")+initial+"' is ambiguous");
|
||||
return false;
|
||||
}
|
||||
else lookup[initial]=p->first;
|
||||
}
|
||||
}
|
||||
|
||||
for (int i=1; i<argc; i++){
|
||||
if (strncmp(argv[i], "--", 2)==0){
|
||||
const char *p=strchr(argv[i]+2, '=');
|
||||
if (p){
|
||||
std::string name(argv[i]+2, p);
|
||||
std::string val(p+1);
|
||||
set_option(name, val);
|
||||
}
|
||||
else{
|
||||
std::string name(argv[i]+2);
|
||||
if (options.count(name)==0){
|
||||
errors.push_back("undefined option: --"+name);
|
||||
continue;
|
||||
}
|
||||
if (options[name]->has_value()){
|
||||
if (i+1>=argc){
|
||||
errors.push_back("option needs value: --"+name);
|
||||
continue;
|
||||
}
|
||||
else{
|
||||
i++;
|
||||
set_option(name, argv[i]);
|
||||
}
|
||||
}
|
||||
else{
|
||||
set_option(name);
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (strncmp(argv[i], "-", 1)==0){
|
||||
if (!argv[i][1]) continue;
|
||||
char last=argv[i][1];
|
||||
for (int j=2; argv[i][j]; j++){
|
||||
last=argv[i][j];
|
||||
if (lookup.count(argv[i][j-1])==0){
|
||||
errors.push_back(std::string("undefined short option: -")+argv[i][j-1]);
|
||||
continue;
|
||||
}
|
||||
if (lookup[argv[i][j-1]]==""){
|
||||
errors.push_back(std::string("ambiguous short option: -")+argv[i][j-1]);
|
||||
continue;
|
||||
}
|
||||
set_option(lookup[argv[i][j-1]]);
|
||||
}
|
||||
|
||||
if (lookup.count(last)==0){
|
||||
errors.push_back(std::string("undefined short option: -")+last);
|
||||
continue;
|
||||
}
|
||||
if (lookup[last]==""){
|
||||
errors.push_back(std::string("ambiguous short option: -")+last);
|
||||
continue;
|
||||
}
|
||||
|
||||
if (i+1<argc && options[lookup[last]]->has_value()){
|
||||
set_option(lookup[last], argv[i+1]);
|
||||
i++;
|
||||
}
|
||||
else{
|
||||
set_option(lookup[last]);
|
||||
}
|
||||
}
|
||||
else{
|
||||
others.push_back(argv[i]);
|
||||
}
|
||||
}
|
||||
|
||||
for (std::map<std::string, option_base*>::iterator p=options.begin();
|
||||
p!=options.end(); p++)
|
||||
if (!p->second->valid())
|
||||
errors.push_back("need option: --"+std::string(p->first));
|
||||
|
||||
return errors.size()==0;
|
||||
}
|
||||
|
||||
void parse_check(const std::string &arg){
|
||||
if (!options.count("help"))
|
||||
add("help", '?', "print this message");
|
||||
check(0, parse(arg));
|
||||
}
|
||||
|
||||
void parse_check(const std::vector<std::string> &args){
|
||||
if (!options.count("help"))
|
||||
add("help", '?', "print this message");
|
||||
check(args.size(), parse(args));
|
||||
}
|
||||
|
||||
void parse_check(int argc, char *argv[]){
|
||||
if (!options.count("help"))
|
||||
add("help", '?', "print this message");
|
||||
check(argc, parse(argc, argv));
|
||||
}
|
||||
|
||||
std::string error() const{
|
||||
return errors.size()>0?errors[0]:"";
|
||||
}
|
||||
|
||||
std::string error_full() const{
|
||||
std::ostringstream oss;
|
||||
for (size_t i=0; i<errors.size(); i++)
|
||||
oss<<errors[i]<<std::endl;
|
||||
return oss.str();
|
||||
}
|
||||
|
||||
std::string usage() const {
|
||||
std::ostringstream oss;
|
||||
oss<<"usage: "<<prog_name<<" ";
|
||||
for (size_t i=0; i<ordered.size(); i++){
|
||||
if (ordered[i]->must())
|
||||
oss<<ordered[i]->short_description()<<" ";
|
||||
}
|
||||
|
||||
oss<<"[options] ... "<<ftr<<std::endl;
|
||||
oss<<"options:"<<std::endl;
|
||||
|
||||
size_t max_width=0;
|
||||
for (size_t i=0; i<ordered.size(); i++){
|
||||
max_width=std::max(max_width, ordered[i]->name().length());
|
||||
}
|
||||
for (size_t i=0; i<ordered.size(); i++){
|
||||
if (ordered[i]->short_name()){
|
||||
oss<<" -"<<ordered[i]->short_name()<<", ";
|
||||
}
|
||||
else{
|
||||
oss<<" ";
|
||||
}
|
||||
|
||||
oss<<"--"<<ordered[i]->name();
|
||||
for (size_t j=ordered[i]->name().length(); j<max_width+4; j++)
|
||||
oss<<' ';
|
||||
oss<<ordered[i]->description()<<std::endl;
|
||||
}
|
||||
return oss.str();
|
||||
}
|
||||
|
||||
private:
|
||||
|
||||
void check(int argc, bool ok){
|
||||
if ((argc==1 && !ok) || exist("help")){
|
||||
std::cerr<<usage();
|
||||
exit(0);
|
||||
}
|
||||
|
||||
if (!ok){
|
||||
std::cerr<<error()<<std::endl<<usage();
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
void set_option(const std::string &name){
|
||||
if (options.count(name)==0){
|
||||
errors.push_back("undefined option: --"+name);
|
||||
return;
|
||||
}
|
||||
if (!options[name]->set()){
|
||||
errors.push_back("option needs value: --"+name);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
void set_option(const std::string &name, const std::string &value){
|
||||
if (options.count(name)==0){
|
||||
errors.push_back("undefined option: --"+name);
|
||||
return;
|
||||
}
|
||||
if (!options[name]->set(value)){
|
||||
errors.push_back("option value is invalid: --"+name+"="+value);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
class option_base{
|
||||
public:
|
||||
virtual ~option_base(){}
|
||||
|
||||
virtual bool has_value() const=0;
|
||||
virtual bool set()=0;
|
||||
virtual bool set(const std::string &value)=0;
|
||||
virtual bool has_set() const=0;
|
||||
virtual bool valid() const=0;
|
||||
virtual bool must() const=0;
|
||||
|
||||
virtual const std::string &name() const=0;
|
||||
virtual char short_name() const=0;
|
||||
virtual const std::string &description() const=0;
|
||||
virtual std::string short_description() const=0;
|
||||
};
|
||||
|
||||
class option_without_value : public option_base {
|
||||
public:
|
||||
option_without_value(const std::string &name,
|
||||
char short_name,
|
||||
const std::string &desc)
|
||||
:nam(name), snam(short_name), desc(desc), has(false){
|
||||
}
|
||||
~option_without_value(){}
|
||||
|
||||
bool has_value() const { return false; }
|
||||
|
||||
bool set(){
|
||||
has=true;
|
||||
return true;
|
||||
}
|
||||
|
||||
bool set(const std::string &){
|
||||
return false;
|
||||
}
|
||||
|
||||
bool has_set() const {
|
||||
return has;
|
||||
}
|
||||
|
||||
bool valid() const{
|
||||
return true;
|
||||
}
|
||||
|
||||
bool must() const{
|
||||
return false;
|
||||
}
|
||||
|
||||
const std::string &name() const{
|
||||
return nam;
|
||||
}
|
||||
|
||||
char short_name() const{
|
||||
return snam;
|
||||
}
|
||||
|
||||
const std::string &description() const {
|
||||
return desc;
|
||||
}
|
||||
|
||||
std::string short_description() const{
|
||||
return "--"+nam;
|
||||
}
|
||||
|
||||
private:
|
||||
std::string nam;
|
||||
char snam;
|
||||
std::string desc;
|
||||
bool has;
|
||||
};
|
||||
|
||||
template <class T>
|
||||
class option_with_value : public option_base {
|
||||
public:
|
||||
option_with_value(const std::string &name,
|
||||
char short_name,
|
||||
bool need,
|
||||
const T &def,
|
||||
const std::string &desc)
|
||||
: nam(name), snam(short_name), need(need), has(false)
|
||||
, def(def), actual(def) {
|
||||
this->desc=full_description(desc);
|
||||
}
|
||||
~option_with_value(){}
|
||||
|
||||
const T &get() const {
|
||||
return actual;
|
||||
}
|
||||
|
||||
bool has_value() const { return true; }
|
||||
|
||||
bool set(){
|
||||
return false;
|
||||
}
|
||||
|
||||
bool set(const std::string &value){
|
||||
try{
|
||||
actual=read(value);
|
||||
has=true;
|
||||
}
|
||||
catch(const std::exception &e){
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool has_set() const{
|
||||
return has;
|
||||
}
|
||||
|
||||
bool valid() const{
|
||||
if (need && !has) return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
bool must() const{
|
||||
return need;
|
||||
}
|
||||
|
||||
const std::string &name() const{
|
||||
return nam;
|
||||
}
|
||||
|
||||
char short_name() const{
|
||||
return snam;
|
||||
}
|
||||
|
||||
const std::string &description() const {
|
||||
return desc;
|
||||
}
|
||||
|
||||
std::string short_description() const{
|
||||
return "--"+nam+"="+detail::readable_typename<T>();
|
||||
}
|
||||
|
||||
protected:
|
||||
std::string full_description(const std::string &desc){
|
||||
return
|
||||
desc+" ("+detail::readable_typename<T>()+
|
||||
(need?"":" [="+detail::default_value<T>(def)+"]")
|
||||
+")";
|
||||
}
|
||||
|
||||
virtual T read(const std::string &s)=0;
|
||||
|
||||
std::string nam;
|
||||
char snam;
|
||||
bool need;
|
||||
std::string desc;
|
||||
|
||||
bool has;
|
||||
T def;
|
||||
T actual;
|
||||
};
|
||||
|
||||
template <class T, class F>
|
||||
class option_with_value_with_reader : public option_with_value<T> {
|
||||
public:
|
||||
option_with_value_with_reader(const std::string &name,
|
||||
char short_name,
|
||||
bool need,
|
||||
const T def,
|
||||
const std::string &desc,
|
||||
F reader)
|
||||
: option_with_value<T>(name, short_name, need, def, desc), reader(reader){
|
||||
}
|
||||
|
||||
private:
|
||||
T read(const std::string &s){
|
||||
return reader(s);
|
||||
}
|
||||
|
||||
F reader;
|
||||
};
|
||||
|
||||
std::map<std::string, option_base*> options;
|
||||
std::vector<option_base*> ordered;
|
||||
std::string ftr;
|
||||
|
||||
std::string prog_name;
|
||||
std::vector<std::string> others;
|
||||
|
||||
std::vector<std::string> errors;
|
||||
};
|
||||
|
||||
} // cmdline
|
|
@ -1,325 +0,0 @@
|
|||
// Include GLFW
|
||||
#include <glfw3.h>
|
||||
extern GLFWwindow* window; // The "extern" keyword here is to access the variable "window" declared in tutorialXXX.cpp. This is a hack to keep the tutorials simple. Please avoid this.
|
||||
|
||||
// Include GLM
|
||||
#include <glm/glm.hpp>
|
||||
//#include <glm/gtx/rotate_vector.hpp>
|
||||
#include <glm/gtc/matrix_transform.hpp>
|
||||
#include <glm/gtx/transform.hpp>
|
||||
#include <glm/gtc/quaternion.hpp>
|
||||
#include <glm/gtx/quaternion.hpp>
|
||||
#include <stdio.h>
|
||||
#include <cassert>
|
||||
#include <cstring>
|
||||
|
||||
|
||||
using namespace glm;
|
||||
|
||||
#include "controls.hpp"
|
||||
|
||||
glm::mat4 ViewMatrix;
|
||||
glm::mat4 ProjectionMatrix;
|
||||
|
||||
glm::mat4 getViewMatrix(){
|
||||
return ViewMatrix;
|
||||
}
|
||||
glm::mat4 getProjectionMatrix(){
|
||||
return ProjectionMatrix;
|
||||
}
|
||||
|
||||
|
||||
// Initial horizontal angle : toward -Z
|
||||
float horizontalAngle = 3.14f;
|
||||
// Initial vertical angle : none
|
||||
float verticalAngle = 0.0f;
|
||||
|
||||
float speed = 3.0f; // 3 units / second
|
||||
float mouseSpeed = 0.005f;
|
||||
|
||||
float currentPoseStartTime = 0;
|
||||
int currentPoseRotCount = 0;
|
||||
|
||||
glm::vec3 position;
|
||||
|
||||
glm::quat initialDirections[] = {
|
||||
// glm::quat(glm::vec3(glm::radians(90.0f), 0.0f, 0.0f)),
|
||||
// glm::quat(glm::vec3(0.0f, glm::radians(-90.0f), 0.0f)),
|
||||
// glm::quat(glm::vec3(0.0f, 0.0f, 0.0f)),
|
||||
// glm::quat(glm::vec3(0.0f, glm::radians(90.0f), 0.0f)),
|
||||
// glm::quat(glm::vec3(0.0f, glm::radians(-180.0f), 0.0f)),
|
||||
// glm::quat(glm::vec3(glm::radians(-90.0f), 0.0f, 0.0f))
|
||||
|
||||
glm::quat(glm::vec3(glm::radians(90.0f), 0.0f, 0.0f)),
|
||||
glm::quat(glm::vec3(0.0f, glm::radians(90.0f), 0.0f)),
|
||||
glm::quat(glm::vec3(0.0f, 0.0f, 0.0f)),
|
||||
glm::quat(glm::vec3(0.0f, glm::radians(-90.0f), 0.0f)),
|
||||
glm::quat(glm::vec3(0.0f, glm::radians(-180.0f), 0.0f)),
|
||||
glm::quat(glm::vec3(glm::radians(-90.0f), 0.0f, 0.0f))
|
||||
};
|
||||
|
||||
glm::mat4 getView(glm::mat4 oldCam2world, int k){
|
||||
glm::quat initial = initialDirections[k];
|
||||
glm::mat4 left2right = glm::mat4();
|
||||
left2right[2][2] = -1;
|
||||
|
||||
glm::quat newCam2oldCam = initial;
|
||||
glm::mat4 newCam2World = oldCam2world * glm::toMat4(newCam2oldCam);
|
||||
|
||||
glm::mat4 world2newCam = glm::inverse(newCam2World);
|
||||
|
||||
return world2newCam;
|
||||
}
|
||||
|
||||
// Automatically load all poses of a model, and render corresponding pngs
|
||||
// Useful for diagnostics
|
||||
void getPositionRotation(glm::vec3 &position, float& rotX, float& rotY, float& rotZ, char* filename) {
|
||||
// Change position, rotation and Z value
|
||||
printf("Updating position rotation\n");
|
||||
const char * path = "posefile";
|
||||
FILE * file = fopen(path, "r");
|
||||
if( file == NULL ){
|
||||
printf("Impossible to open the file !\n");
|
||||
}
|
||||
printf("Done reading pose file\n");
|
||||
int i = -1;
|
||||
float pos[3], rot[3];
|
||||
char namebuf[50];
|
||||
while (i < currentPoseRotCount) {
|
||||
//printf("current i: %d\n", i);
|
||||
//printf("original vec %f %f %f\n", position[0], position[1], position[2]);
|
||||
|
||||
memset(namebuf, 0, 50);
|
||||
int count = fscanf(file, "%f %f %f %f %f %f %s\n", &pos[0], &pos[1], &pos[2], &rot[0], &rot[1], &rot[2], namebuf );
|
||||
// printf("current count: %d %s\n", count, namebuf);
|
||||
assert(count == 7);
|
||||
|
||||
//fgets(filename, 30, file);
|
||||
//printf("current count: %d %s\n", count, filename);
|
||||
i ++;
|
||||
}
|
||||
position[0] = pos[0];
|
||||
position[1] = pos[1];
|
||||
position[2] = pos[2];
|
||||
rotX = rot[0];
|
||||
rotY = rot[1];
|
||||
rotZ = rot[2];
|
||||
strcpy(filename, namebuf);
|
||||
printf("Successfully read pose file line %d\n", currentPoseRotCount);
|
||||
fclose(file);
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
bool computeMatricesFromInputs(){
|
||||
|
||||
bool do_screenshot = true;
|
||||
|
||||
// glfwGetTime is called only once, the first time this function is called
|
||||
static double lastTime = glfwGetTime();
|
||||
|
||||
// Compute time difference between current and last frame
|
||||
double currentTime = glfwGetTime();
|
||||
float deltaTime = float(currentTime - lastTime);
|
||||
|
||||
// Get mouse position
|
||||
double xpos, ypos;
|
||||
//glfwGetCursorPos(window, &xpos, &ypos);
|
||||
|
||||
// Reset mouse position for next framAze
|
||||
//glfwSetCursorPos(window, 512/2, 512/2);
|
||||
|
||||
// Compute new orientation
|
||||
horizontalAngle += mouseSpeed * float( 768/2 - xpos );
|
||||
verticalAngle += mouseSpeed * float( 768/2 - ypos );
|
||||
|
||||
// Direction : Spherical coordinates to Cartesian coordinates conversion
|
||||
glm::vec3 direction(
|
||||
cos(verticalAngle) * sin(horizontalAngle),
|
||||
sin(verticalAngle),
|
||||
cos(verticalAngle) * cos(horizontalAngle)
|
||||
);
|
||||
|
||||
// Right vector
|
||||
glm::vec3 right = glm::vec3(
|
||||
sin(horizontalAngle - 3.14f/2.0f),
|
||||
0,
|
||||
cos(horizontalAngle - 3.14f/2.0f)
|
||||
);
|
||||
|
||||
// Up vector
|
||||
// glm::vec3 up = glm::cross( right, direction );
|
||||
glm::vec4 up4 = glm::vec4(0.0, 1.0, 0.0, 1.0);
|
||||
|
||||
/*
|
||||
// Move forward
|
||||
if (glfwGetKey( window, GLFW_KEY_UP ) == GLFW_PRESS){
|
||||
position += direction * deltaTime * speed;
|
||||
}
|
||||
// Move backward
|
||||
if (glfwGetKey( window, GLFW_KEY_DOWN ) == GLFW_PRESS){
|
||||
position -= direction * deltaTime * speed;
|
||||
}
|
||||
// Strafe right
|
||||
if (glfwGetKey( window, GLFW_KEY_RIGHT ) == GLFW_PRESS){
|
||||
position += right * deltaTime * speed;
|
||||
}
|
||||
// Strafe left
|
||||
if (glfwGetKey( window, GLFW_KEY_LEFT ) == GLFW_PRESS){
|
||||
position -= right * deltaTime * speed;
|
||||
}
|
||||
*/
|
||||
|
||||
|
||||
// Hardcoded pose information
|
||||
// Camera matrix
|
||||
// Point 0 view 1
|
||||
/*float rotationX = 1.2462860345840454;
|
||||
float rotationY = -0.009244712069630623;
|
||||
float rotationZ = -1.2957184314727783;
|
||||
*/
|
||||
// Point 0 view 2
|
||||
float rotationX = 1.3605239391326904;
|
||||
float rotationY = -0.009078502655029297;
|
||||
float rotationZ = -1.441698670387268;
|
||||
//float fov = 0.9698680134771724;
|
||||
float fov = glm::radians(90.0f);
|
||||
|
||||
|
||||
ProjectionMatrix = glm::perspective(fov, 1.0f, 0.1f, 5000.0f); // near & far are not verified, but accuracy seems to work well
|
||||
|
||||
// Point 6 view 0
|
||||
//float rotationX = 1.4468656778335571;
|
||||
//float rotationY = -0.00613052025437355;
|
||||
//float rotationZ = -0.22472861409187317;
|
||||
|
||||
|
||||
//if (currentTime - currentPoseStartTime > 1) {
|
||||
// UNCOMMENT THIS, in order to render png at a new position every second
|
||||
//getPositionRotation(position, rotationX, rotationY, rotationZ, filename);
|
||||
glm::quat initial = initialDirections[currentPoseRotCount];
|
||||
//convertRotation(rotationX, rotationY, rotationZ, currentPoseRotCount);
|
||||
currentPoseStartTime = currentTime;
|
||||
currentPoseRotCount += 1;
|
||||
do_screenshot = true;
|
||||
//}
|
||||
|
||||
|
||||
|
||||
glm::quat viewDirection;
|
||||
glm::vec3 viewDirectionEuler(rotationX, rotationY, rotationZ);
|
||||
viewDirection = glm::quat(viewDirectionEuler) * initial;
|
||||
|
||||
ViewMatrix = glm::inverse(glm::translate(glm::mat4(1.0), position) * glm::toMat4(viewDirection));
|
||||
|
||||
/*printf("Third view matrix\n");
|
||||
for (int i = 0; i < 4; ++i) {
|
||||
printf("\t %f %f %f %f\n", ViewMatrix[0][i], ViewMatrix[1][i], ViewMatrix[2][i], ViewMatrix[3][i]);
|
||||
}*/
|
||||
|
||||
// For the next frame, the "last time" will be "now"
|
||||
lastTime = currentTime;
|
||||
|
||||
return do_screenshot;
|
||||
}
|
||||
|
||||
|
||||
bool computeMatricesFromFile(std::string filename){
|
||||
|
||||
bool do_screenshot = true;
|
||||
|
||||
|
||||
// glfwGetTime is called only once, the first time this function is called
|
||||
static double lastTime = glfwGetTime();
|
||||
|
||||
// Compute time difference between current and last frame
|
||||
double currentTime = glfwGetTime();
|
||||
float deltaTime = float(currentTime - lastTime);
|
||||
|
||||
// Get mouse position
|
||||
double xpos, ypos;
|
||||
|
||||
|
||||
// Compute new orientation
|
||||
horizontalAngle += mouseSpeed * float( 512/2 - xpos );
|
||||
verticalAngle += mouseSpeed * float( 512/2 - ypos );
|
||||
|
||||
// Direction : Spherical coordinates to Cartesian coordinates conversion
|
||||
glm::vec3 direction(
|
||||
cos(verticalAngle) * sin(horizontalAngle),
|
||||
sin(verticalAngle),
|
||||
cos(verticalAngle) * cos(horizontalAngle)
|
||||
);
|
||||
|
||||
// Hardcoded pose information
|
||||
// Camera matrix
|
||||
// Point 0 view 1
|
||||
/*float rotationX = 1.2462860345840454;
|
||||
float rotationY = -0.009244712069630623;
|
||||
float rotationZ = -1.2957184314727783;
|
||||
*/
|
||||
// Point 0 view 2
|
||||
//float rotationX = 1.3605239391326904;
|
||||
//float rotationY = -0.009078502655029297;
|
||||
//float rotationZ = -1.441698670387268;
|
||||
//float fov = 0.9698680134771724;
|
||||
float fov = glm::radians(90.0f);
|
||||
|
||||
float posX = 0;
|
||||
float posY = 0;
|
||||
float posZ = 0;
|
||||
|
||||
float rotW = 0;
|
||||
float rotX = 0;
|
||||
float rotY = 0;
|
||||
float rotZ = 0;
|
||||
|
||||
float junk[2];
|
||||
|
||||
FILE * file = fopen(filename.c_str(), "r");
|
||||
if( file == NULL ){
|
||||
printf("Impossible to open pose file %s!\n", filename.c_str());
|
||||
}
|
||||
|
||||
char namebuf[50];
|
||||
|
||||
int count = fscanf(file, "%s %f %f %f %f %f %f %f %f %f\n", namebuf, &posX, &posY, &posZ, &rotX, &rotY, &rotZ, &rotW, &junk[0], &junk[1] );
|
||||
|
||||
printf("Loading pose file count: %d, namebuf: %s, rot count %d, (%f, %f, %f, %f)\n", count, namebuf, currentPoseRotCount, rotW, rotX, rotY, rotZ);
|
||||
|
||||
//assert(count == 10);
|
||||
|
||||
//rotY = -rotY;
|
||||
|
||||
position = glm::vec3(posX, posY, posZ);
|
||||
|
||||
ProjectionMatrix = glm::perspective(fov, 1.0f, 0.1f, 5000.0f); // near & far are not verified, but accuracy seems to work well
|
||||
|
||||
|
||||
//if (currentTime - currentPoseStartTime > 1) {
|
||||
// UNCOMMENT THIS, in order to render png at a new position every second
|
||||
//getPositionRotation(position, rotationX, rotationY, rotationZ, filename);
|
||||
glm::quat initial = initialDirections[currentPoseRotCount % 6];
|
||||
//convertRotation(rotationX, rotationY, rotationZ, currentPoseRotCount);
|
||||
currentPoseStartTime = currentTime;
|
||||
currentPoseRotCount += 1;
|
||||
do_screenshot = true;
|
||||
//}
|
||||
|
||||
|
||||
glm::quat viewDirection;
|
||||
//glm::vec3 viewDirectionEuler(rotationX, rotationY, rotationZ);
|
||||
glm::quat rotateX_90 = glm::quat(glm::vec3(glm::radians(90.0f), 0.0f, 0.0f));
|
||||
//viewDirection = rotateX_90 * glm::quat(rotW, rotX, rotY, rotZ) * initial;
|
||||
viewDirection = glm::quat(rotW, rotX, rotY, rotZ) * initial;
|
||||
//viewDirection = glm::quat(viewDirectionEuler) * initial;
|
||||
|
||||
ViewMatrix = glm::inverse(glm::translate(glm::mat4(1.0), position) * glm::toMat4(viewDirection));
|
||||
|
||||
// For the next frame, the "last time" will be "now"
|
||||
lastTime = currentTime;
|
||||
|
||||
return do_screenshot;
|
||||
}
|
||||
|
|
@ -1,14 +0,0 @@
|
|||
#ifndef CONTROLS_HPP
|
||||
#define CONTROLS_HPP
|
||||
|
||||
#include <string>
|
||||
|
||||
bool computeMatricesFromInputs();
|
||||
bool computeMatricesFromFile(std::string filename);
|
||||
|
||||
glm::mat4 getViewMatrix();
|
||||
glm::mat4 getProjectionMatrix();
|
||||
|
||||
glm::mat4 getView(glm::mat4 source, int k);
|
||||
|
||||
#endif
|
|
@ -1,267 +0,0 @@
|
|||
#include <vector>
|
||||
#include <stdio.h>
|
||||
#include <string>
|
||||
#include <cstring>
|
||||
#include <iostream>
|
||||
#include <glm/glm.hpp>
|
||||
|
||||
#include "objloader.hpp"
|
||||
|
||||
// Very, VERY simple OBJ loader.
|
||||
// Here is a short list of features a real function would provide :
|
||||
// - Binary files. Reading a model should be just a few memcpy's away, not parsing a file at runtime. In short : OBJ is not very great.
|
||||
// - Animations & bones (includes bones weights)
|
||||
// - Multiple UVs
|
||||
// - All attributes should be optional, not "forced"
|
||||
// - More stable. Change a line in the OBJ file and it crashes.
|
||||
// - More secure. Change another line and you can inject code.
|
||||
// - Loading from memory, stream, etc
|
||||
|
||||
bool loadOBJ(
|
||||
const char * path,
|
||||
std::vector<glm::vec3> & out_vertices,
|
||||
std::vector<glm::vec2> & out_uvs,
|
||||
std::vector<glm::vec3> & out_normals
|
||||
){
|
||||
//printf("Loading OBJ file %s...\n", path);
|
||||
|
||||
std::vector<unsigned int> vertexIndices, uvIndices, normalIndices;
|
||||
std::vector<glm::vec3> temp_vertices;
|
||||
std::vector<glm::vec2> temp_uvs;
|
||||
std::vector<glm::vec3> temp_normals;
|
||||
|
||||
FILE * file = fopen(path, "r");
|
||||
if( file == NULL ){
|
||||
printf("Impossible to open the file %s\n", path);
|
||||
getchar();
|
||||
return false;
|
||||
}
|
||||
|
||||
unsigned int v_count = 0;
|
||||
|
||||
while( 1 ){
|
||||
|
||||
char lineHeader[128];
|
||||
// read the first word of the line
|
||||
int res = fscanf(file, "%s", lineHeader);
|
||||
if (res == EOF)
|
||||
break; // EOF = End Of File. Quit the loop.
|
||||
|
||||
// else : parse lineHeader
|
||||
|
||||
if ( strcmp( lineHeader, "v" ) == 0 ){
|
||||
v_count ++;
|
||||
glm::vec3 vertex;
|
||||
//fscanf(file, "%f %f %f\n", &vertex.x, &vertex.y, &vertex.z );
|
||||
// opengl = blender rotate around x at 90
|
||||
fscanf(file, "%f %f %f\n", &vertex.x, &vertex.z, &vertex.y);
|
||||
vertex.y = -vertex.y;
|
||||
temp_vertices.push_back(vertex);
|
||||
}else if ( strcmp( lineHeader, "vt" ) == 0 ){
|
||||
glm::vec2 uv;
|
||||
fscanf(file, "%f %f\n", &uv.x, &uv.y );
|
||||
uv.y = -uv.y; // Invert V coordinate since we will only use DDS texture, which are inverted. Remove if you want to use TGA or BMP loaders.
|
||||
temp_uvs.push_back(uv);
|
||||
}else if ( strcmp( lineHeader, "vn" ) == 0 ){
|
||||
glm::vec3 normal;
|
||||
fscanf(file, "%f %f %f\n", &normal.x, &normal.y, &normal.z );
|
||||
temp_normals.push_back(normal);
|
||||
}else if ( strcmp( lineHeader, "f" ) == 0 ){
|
||||
std::string vertex1, vertex2, vertex3;
|
||||
unsigned int vertexIndex[3], uvIndex[3], normalIndex[3];
|
||||
char stringBuffer[500];
|
||||
fgets(stringBuffer, 500, file);
|
||||
//int matches = fscanf(file, "%u/%u/%u %u/%u/%u %u/%u/%u\n", &vertexIndex[0], &uvIndex[0], &normalIndex[0], &vertexIndex[1], &uvIndex[1], &normalIndex[1], &vertexIndex[2], &uvIndex[2], &normalIndex[2] );
|
||||
int matches = sscanf(stringBuffer, "%u/%u/%u %u/%u/%u %u/%u/%u\n", &vertexIndex[0], &uvIndex[0], &normalIndex[0], &vertexIndex[1], &uvIndex[1], &normalIndex[1], &vertexIndex[2], &uvIndex[2], &normalIndex[2] );
|
||||
bool f_3_format = (matches == 9);
|
||||
bool f_2_format = true;
|
||||
bool f_2_format_normal = true;
|
||||
if (! f_3_format) {
|
||||
// .obj file has `f v1/uv1 v2/uv2 v3/uv3` format
|
||||
int matches = sscanf(stringBuffer, " %u/%u %u/%u %u/%u\n", &vertexIndex[0], &uvIndex[0], &vertexIndex[1], &uvIndex[1], &vertexIndex[2], &uvIndex[2] );
|
||||
f_2_format = (matches == 6);
|
||||
if (! f_2_format) {
|
||||
int matches = sscanf(stringBuffer, " %u//%u %u//%u %u//%u\n", &vertexIndex[0], &normalIndex[0], &vertexIndex[1], &normalIndex[1], &vertexIndex[2], &normalIndex[2] );
|
||||
f_2_format_normal = (matches == 6);
|
||||
if (! f_2_format_normal) {
|
||||
int matches = sscanf(stringBuffer, " %u %u %u\n", &vertexIndex[0], &vertexIndex[1], &vertexIndex[2]);
|
||||
if (matches != 3){
|
||||
printf("File %s can't be read by our simple parser :-( Try exporting with other options\n", path);
|
||||
fclose(file);
|
||||
return false;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
vertexIndices.push_back(vertexIndex[0]);
|
||||
vertexIndices.push_back(vertexIndex[1]);
|
||||
vertexIndices.push_back(vertexIndex[2]);
|
||||
if (f_2_format || f_3_format) {
|
||||
uvIndices .push_back(uvIndex[0]);
|
||||
uvIndices .push_back(uvIndex[1]);
|
||||
uvIndices .push_back(uvIndex[2]);
|
||||
}
|
||||
if (f_3_format || f_2_format_normal) {
|
||||
normalIndices.push_back(normalIndex[0]);
|
||||
normalIndices.push_back(normalIndex[1]);
|
||||
normalIndices.push_back(normalIndex[2]);
|
||||
}
|
||||
}else{
|
||||
// Probably a comment, eat up the rest of the line
|
||||
char stupidBuffer[1000];
|
||||
fgets(stupidBuffer, 1000, file);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// For each vertex of each triangle
|
||||
for( unsigned int i=0; i<vertexIndices.size(); i++ ){
|
||||
|
||||
// Get the indices of its attributes
|
||||
unsigned int vertexIndex = vertexIndices[i];
|
||||
unsigned int uvIndex = -1;
|
||||
|
||||
if (uvIndices.size() > 0)
|
||||
uvIndex = uvIndices[i];
|
||||
|
||||
unsigned int normalIndex = -1;
|
||||
if (normalIndices.size() > 0)
|
||||
normalIndex = normalIndices[i];
|
||||
|
||||
|
||||
// Get the attributes thanks to the index
|
||||
glm::vec3 vertex = temp_vertices[ vertexIndex-1 ];
|
||||
|
||||
|
||||
// Put the attributes in buffers
|
||||
out_vertices.push_back(vertex);
|
||||
|
||||
if (temp_uvs.size() > 0 && uvIndices.size() > 0) {
|
||||
glm::vec2 uv = temp_uvs[ uvIndex-1 ];
|
||||
out_uvs .push_back(uv);
|
||||
}
|
||||
|
||||
if (temp_normals.size() > 0 && normalIndices.size() > 0) {
|
||||
glm::vec3 normal = temp_normals[ normalIndex-1 ];
|
||||
out_normals.push_back(normal);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// construct the temp_normals vector here, using vertex positions and face vertex indices
|
||||
// TODO: this is not well-tested yet
|
||||
std::vector<unsigned int> vertexFaces(temp_vertices.size());
|
||||
std::fill(vertexFaces.begin(), vertexFaces.end(), 0);
|
||||
|
||||
if ( out_normals.size() == 0 ) {
|
||||
for ( unsigned int i=0; i<out_vertices.size(); i++ ){
|
||||
out_normals.push_back(glm::vec3(0.0));
|
||||
}
|
||||
|
||||
for ( unsigned int i=0; i<vertexIndices.size(); i++ ) {
|
||||
vertexFaces[vertexIndices[i]] += 1;
|
||||
}
|
||||
|
||||
|
||||
for ( unsigned int i=0; i<vertexIndices.size(); i++ ){
|
||||
// make sure vertices are arranged in right hand order
|
||||
unsigned int v1 = i;
|
||||
unsigned int v2 = ((v1+1)%3==0) ? (v1-2) : (v1+1);
|
||||
unsigned int v3 = ((v2+1)%3==0) ? (v2-2) : (v2+1);
|
||||
|
||||
//std::cout << "v1 " << v1 << " v2 " << v2 << " v3 " << v3 << std::endl;
|
||||
glm::vec3 edge1 = out_vertices[v2] - out_vertices[v1];
|
||||
//glm::vec3 edge2 = out_vertices[v3] - out_vertices[v2];
|
||||
glm::vec3 edge2 = out_vertices[v3] - out_vertices[v1];
|
||||
|
||||
// set normal as cross product
|
||||
unsigned int vertexIndex = vertexIndices[i];
|
||||
glm::vec3 normal = glm::normalize(glm::cross(edge1, edge2));
|
||||
//std::cout << normal.x << " " << normal.y << " " << normal.z << " " << normal.x * normal.x + normal.y * normal.y + normal.z * normal.z << " " << float(vertexFaces[vertexIndex-1]) << std::endl;
|
||||
out_normals[i] += normal / float(vertexFaces[vertexIndex-1]);
|
||||
|
||||
//std::cout << "Writing to " << vertexIndex << std::endl;
|
||||
//out_normals[vertexIndex-1] = glm::vec3(1, 0, 0);
|
||||
}
|
||||
|
||||
// Renormalize all the normal vectors
|
||||
for (unsigned int i=0; i<out_normals.size(); i++) {
|
||||
out_normals[i] = glm::normalize(out_normals[i]);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// TODO: (hzyjerry) this is a dummy place holder
|
||||
if ( out_uvs.size() == 0 ) {
|
||||
for ( unsigned int i=0; i<out_vertices.size(); i++ ){
|
||||
out_uvs.push_back(glm::vec2(0.0));
|
||||
}
|
||||
}
|
||||
//printf("size of temp vertices %lu, vertex indices %lu out vertices %lu\n", temp_vertices.size(), vertexIndices.size(), out_vertices.size());
|
||||
fclose(file);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
#ifdef USE_ASSIMP // don't use this #define, it's only for me (it AssImp fails to compile on your machine, at least all the other tutorials still work)
|
||||
|
||||
// Include AssImp
|
||||
#include <assimp/Importer.hpp> // C++ importer interface
|
||||
#include <assimp/scene.h> // Output data structure
|
||||
#include <assimp/postprocess.h> // Post processing flags
|
||||
|
||||
bool loadAssImp(
|
||||
const char * path,
|
||||
std::vector<unsigned short> & indices,
|
||||
std::vector<glm::vec3> & vertices,
|
||||
std::vector<glm::vec2> & uvs,
|
||||
std::vector<glm::vec3> & normals
|
||||
){
|
||||
|
||||
Assimp::Importer importer;
|
||||
|
||||
const aiScene* scene = importer.ReadFile(path, 0/*aiProcess_JoinIdenticalVertices | aiProcess_SortByPType*/);
|
||||
if( !scene) {
|
||||
fprintf( stderr, importer.GetErrorString());
|
||||
getchar();
|
||||
return false;
|
||||
}
|
||||
const aiMesh* mesh = scene->mMeshes[0]; // In this simple example code we always use the 1rst mesh (in OBJ files there is often only one anyway)
|
||||
|
||||
// Fill vertices positions
|
||||
vertices.reserve(mesh->mNumVertices);
|
||||
for(unsigned int i=0; i<mesh->mNumVertices; i++){
|
||||
aiVector3D pos = mesh->mVertices[i];
|
||||
vertices.push_back(glm::vec3(pos.x, pos.y, pos.z));
|
||||
}
|
||||
|
||||
// Fill vertices texture coordinates
|
||||
uvs.reserve(mesh->mNumVertices);
|
||||
for(unsigned int i=0; i<mesh->mNumVertices; i++){
|
||||
aiVector3D UVW = mesh->mTextureCoords[0][i]; // Assume only 1 set of UV coords; AssImp supports 8 UV sets.
|
||||
uvs.push_back(glm::vec2(UVW.x, UVW.y));
|
||||
}
|
||||
|
||||
// Fill vertices normals
|
||||
normals.reserve(mesh->mNumVertices);
|
||||
for(unsigned int i=0; i<mesh->mNumVertices; i++){
|
||||
aiVector3D n = mesh->mNormals[i];
|
||||
normals.push_back(glm::vec3(n.x, n.y, n.z));
|
||||
}
|
||||
|
||||
|
||||
// Fill face indices
|
||||
indices.reserve(3*mesh->mNumFaces);
|
||||
for (unsigned int i=0; i<mesh->mNumFaces; i++){
|
||||
// Assume the model has only triangles.
|
||||
indices.push_back(mesh->mFaces[i].mIndices[0]);
|
||||
indices.push_back(mesh->mFaces[i].mIndices[1]);
|
||||
indices.push_back(mesh->mFaces[i].mIndices[2]);
|
||||
}
|
||||
|
||||
// The "scene" pointer will be deleted automatically by "importer"
|
||||
return true;
|
||||
}
|
||||
|
||||
#endif
|
|
@ -1,21 +0,0 @@
|
|||
#ifndef OBJLOADER_H
|
||||
#define OBJLOADER_H
|
||||
|
||||
bool loadOBJ(
|
||||
const char * path,
|
||||
std::vector<glm::vec3> & out_vertices,
|
||||
std::vector<glm::vec2> & out_uvs,
|
||||
std::vector<glm::vec3> & out_normals
|
||||
);
|
||||
|
||||
|
||||
|
||||
bool loadAssImp(
|
||||
const char * path,
|
||||
std::vector<unsigned short> & indices,
|
||||
std::vector<glm::vec3> & vertices,
|
||||
std::vector<glm::vec2> & uvs,
|
||||
std::vector<glm::vec3> & normals
|
||||
);
|
||||
|
||||
#endif
|
File diff suppressed because it is too large
Load Diff
|
@ -1,164 +0,0 @@
|
|||
#include <glm/gtc/quaternion.hpp>
|
||||
#include <glm/gtx/quaternion.hpp>
|
||||
#include <glm/gtx/euler_angles.hpp>
|
||||
#include <glm/gtx/norm.hpp>
|
||||
using namespace glm;
|
||||
|
||||
#include "quaternion_utils.hpp"
|
||||
|
||||
|
||||
// Returns a quaternion such that q*start = dest
|
||||
quat RotationBetweenVectors(vec3 start, vec3 dest){
|
||||
start = normalize(start);
|
||||
dest = normalize(dest);
|
||||
|
||||
float cosTheta = dot(start, dest);
|
||||
vec3 rotationAxis;
|
||||
|
||||
if (cosTheta < -1 + 0.001f){
|
||||
// special case when vectors in opposite directions :
|
||||
// there is no "ideal" rotation axis
|
||||
// So guess one; any will do as long as it's perpendicular to start
|
||||
// This implementation favors a rotation around the Up axis,
|
||||
// since it's often what you want to do.
|
||||
rotationAxis = cross(vec3(0.0f, 0.0f, 1.0f), start);
|
||||
if (length2(rotationAxis) < 0.01 ) // bad luck, they were parallel, try again!
|
||||
rotationAxis = cross(vec3(1.0f, 0.0f, 0.0f), start);
|
||||
|
||||
rotationAxis = normalize(rotationAxis);
|
||||
return angleAxis(glm::radians(180.0f), rotationAxis);
|
||||
}
|
||||
|
||||
// Implementation from Stan Melax's Game Programming Gems 1 article
|
||||
rotationAxis = cross(start, dest);
|
||||
|
||||
float s = sqrt( (1+cosTheta)*2 );
|
||||
float invs = 1 / s;
|
||||
|
||||
return quat(
|
||||
s * 0.5f,
|
||||
rotationAxis.x * invs,
|
||||
rotationAxis.y * invs,
|
||||
rotationAxis.z * invs
|
||||
);
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
// Returns a quaternion that will make your object looking towards 'direction'.
|
||||
// Similar to RotationBetweenVectors, but also controls the vertical orientation.
|
||||
// This assumes that at rest, the object faces +Z.
|
||||
// Beware, the first parameter is a direction, not the target point !
|
||||
quat LookAt(vec3 direction, vec3 desiredUp){
|
||||
|
||||
if (length2(direction) < 0.0001f )
|
||||
return quat();
|
||||
|
||||
// Recompute desiredUp so that it's perpendicular to the direction
|
||||
// You can skip that part if you really want to force desiredUp
|
||||
vec3 right = cross(direction, desiredUp);
|
||||
desiredUp = cross(right, direction);
|
||||
|
||||
// Find the rotation between the front of the object (that we assume towards +Z,
|
||||
// but this depends on your model) and the desired direction
|
||||
quat rot1 = RotationBetweenVectors(vec3(0.0f, 0.0f, 1.0f), direction);
|
||||
// Because of the 1rst rotation, the up is probably completely screwed up.
|
||||
// Find the rotation between the "up" of the rotated object, and the desired up
|
||||
vec3 newUp = rot1 * vec3(0.0f, 1.0f, 0.0f);
|
||||
quat rot2 = RotationBetweenVectors(newUp, desiredUp);
|
||||
|
||||
// Apply them
|
||||
return rot2 * rot1; // remember, in reverse order.
|
||||
}
|
||||
|
||||
|
||||
|
||||
// Like SLERP, but forbids rotation greater than maxAngle (in radians)
|
||||
// In conjunction to LookAt, can make your characters
|
||||
quat RotateTowards(quat q1, quat q2, float maxAngle){
|
||||
|
||||
if( maxAngle < 0.001f ){
|
||||
// No rotation allowed. Prevent dividing by 0 later.
|
||||
return q1;
|
||||
}
|
||||
|
||||
float cosTheta = dot(q1, q2);
|
||||
|
||||
// q1 and q2 are already equal.
|
||||
// Force q2 just to be sure
|
||||
if(cosTheta > 0.9999f){
|
||||
return q2;
|
||||
}
|
||||
|
||||
// Avoid taking the long path around the sphere
|
||||
if (cosTheta < 0){
|
||||
q1 = q1*-1.0f;
|
||||
cosTheta *= -1.0f;
|
||||
}
|
||||
|
||||
float angle = acos(cosTheta);
|
||||
|
||||
// If there is only a 2<> difference, and we are allowed 5<>,
|
||||
// then we arrived.
|
||||
if (angle < maxAngle){
|
||||
return q2;
|
||||
}
|
||||
|
||||
// This is just like slerp(), but with a custom t
|
||||
float t = maxAngle / angle;
|
||||
angle = maxAngle;
|
||||
|
||||
quat res = (sin((1.0f - t) * angle) * q1 + sin(t * angle) * q2) / sin(angle);
|
||||
res = normalize(res);
|
||||
return res;
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
void tests(){
|
||||
|
||||
glm::vec3 Xpos(+1.0f, 0.0f, 0.0f);
|
||||
glm::vec3 Ypos( 0.0f, +1.0f, 0.0f);
|
||||
glm::vec3 Zpos( 0.0f, 0.0f, +1.0f);
|
||||
glm::vec3 Xneg(-1.0f, 0.0f, 0.0f);
|
||||
glm::vec3 Yneg( 0.0f, -1.0f, 0.0f);
|
||||
glm::vec3 Zneg( 0.0f, 0.0f, -1.0f);
|
||||
|
||||
// Testing standard, easy case
|
||||
// Must be 90<39> rotation on X : 0.7 0 0 0.7
|
||||
quat X90rot = RotationBetweenVectors(Ypos, Zpos);
|
||||
|
||||
// Testing with v1 = v2
|
||||
// Must be identity : 0 0 0 1
|
||||
quat id = RotationBetweenVectors(Xpos, Xpos);
|
||||
|
||||
// Testing with v1 = -v2
|
||||
// Must be 180<38> on +/-Y axis : 0 +/-1 0 0
|
||||
quat Y180rot = RotationBetweenVectors(Xpos, Xneg);
|
||||
|
||||
// Testing with v1 = -v2, but with a "bad first guess"
|
||||
// Must be 180<38> on +/-Y axis : 0 +/-1 0 0
|
||||
quat X180rot = RotationBetweenVectors(Zpos, Zneg);
|
||||
|
||||
|
||||
}
|
|
@ -1,11 +0,0 @@
|
|||
#ifndef QUATERNION_UTILS_H
|
||||
#define QUATERNION_UTILS_H
|
||||
|
||||
quat RotationBetweenVectors(vec3 start, vec3 dest);
|
||||
|
||||
quat LookAt(vec3 direction, vec3 desiredUp);
|
||||
|
||||
quat RotateTowards(quat q1, quat q2, float maxAngle);
|
||||
|
||||
|
||||
#endif // QUATERNION_UTILS_H
|
|
@ -1,343 +0,0 @@
|
|||
#include <cstdlib>
|
||||
//#include <cstdio>
|
||||
#include <stdio.h>
|
||||
#include <vector>
|
||||
#include <algorithm>
|
||||
#include <math.h>
|
||||
#include <omp.h>
|
||||
#include <cuda.h>
|
||||
#include <cuda_runtime_api.h>
|
||||
|
||||
using namespace std;
|
||||
// texture<float, 2, cudaReadModeElementType> inTex;
|
||||
texture<float4, 2, cudaReadModeElementType> inTex;
|
||||
// texture<float, cudaTextureType1D, cudaReadModeElementType> inTex;
|
||||
|
||||
const int TILE_DIM = 32;
|
||||
const int BLOCK_ROWS = 8;
|
||||
|
||||
const int N_THREADS = 64;
|
||||
const int N_BLOCKS = 64;
|
||||
|
||||
__global__ void copy_mem(unsigned char *source, unsigned char *render)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int width = gridDim.x * TILE_DIM;
|
||||
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS)
|
||||
for (int channel = 0; channel < 3; channel ++ )
|
||||
render[3*((y+j)*width + x) + channel] = source[3 * ((y+j)*width + x) + channel];
|
||||
}
|
||||
|
||||
|
||||
__global__ void set_depth(unsigned int *depth)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int width = gridDim.x * TILE_DIM;
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS)
|
||||
depth[(y+j)*width + x] = 65535;
|
||||
}
|
||||
|
||||
|
||||
__global__ void char_to_int(int * img2, unsigned char * img)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int width = gridDim.x * TILE_DIM;
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS)
|
||||
img2[(y+j)*width + x] = img[3*((y+j)*width + x) + 0] * 256 * 256 + img[3*((y+j)*width + x) + 1] * 256 + img[3*((y+j)*width + x) + 2];
|
||||
}
|
||||
|
||||
|
||||
__global__ void int_to_char(int * img2, unsigned char * img)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int width = gridDim.x * TILE_DIM;
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS) {
|
||||
img[3*((y+j)*width + x)] = img2[(y+j)*width + x] / (256*256);
|
||||
img[3*((y+j)*width + x)+1] = img2[(y+j)*width + x] / 256 % 256;
|
||||
img[3*((y+j)*width + x)+2] = img2[(y+j)*width + x] % 256;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
__global__ void to3d_point(float *depth, float *points3d)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int w = gridDim.x * TILE_DIM;
|
||||
int h = w / 2;
|
||||
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS)
|
||||
{
|
||||
|
||||
int iw = x;
|
||||
int ih = y + j;
|
||||
float depth_point = depth[ih*w + iw] * 128.0;
|
||||
float phi = ((float)(ih) + 0.5) / float(h) * M_PI;
|
||||
float theta = ((float)(iw) + 0.5) / float(w) * 2 * M_PI + M_PI;
|
||||
|
||||
points3d[(ih * w + iw) * 4 + 0] = depth_point * sin(phi) * cos(theta);
|
||||
points3d[(ih * w + iw) * 4 + 1] = depth_point * sin(phi) * sin(theta);
|
||||
points3d[(ih * w + iw) * 4 + 2] = depth_point * cos(phi);
|
||||
points3d[(ih * w + iw) * 4 + 3] = 1;
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
__global__ void transform(float *points3d_after, float *points3d, float * transformation_matrix)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int w = gridDim.x * TILE_DIM;
|
||||
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS)
|
||||
{
|
||||
int iw = x;
|
||||
int ih = y + j;
|
||||
for (int ic = 0; ic < 3; ic ++) {
|
||||
points3d_after[(ih * w + iw) * 3 + ic] = points3d[(ih * w + iw) * 4 + 0] * transformation_matrix[4 * ic + 0]
|
||||
+ points3d[(ih * w + iw) * 4 + 1] * transformation_matrix[4 * ic + 1]
|
||||
+ points3d[(ih * w + iw) * 4 + 2] * transformation_matrix[4 * ic + 2]
|
||||
+ points3d[(ih * w + iw) * 4 + 3] * transformation_matrix[4 * ic + 3];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
__global__ void transform2d(float *points3d_after, float *points3d_polar)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int w = gridDim.x * TILE_DIM;
|
||||
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS)
|
||||
{
|
||||
int iw = x;
|
||||
int ih = y + j;
|
||||
float x = points3d_after[(ih * w + iw) * 3 + 0];
|
||||
float y = points3d_after[(ih * w + iw) * 3 + 1];
|
||||
float z = points3d_after[(ih * w + iw) * 3 + 2];
|
||||
|
||||
points3d_polar[(ih * w + iw) * 3 + 0] = sqrt(x * x + y * y + z * z);
|
||||
points3d_polar[(ih * w + iw) * 3 + 1] = atan2(y, x);
|
||||
points3d_polar[(ih * w + iw) * 3 + 2] = atan2(sqrt(x * x + y * y), z);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
__global__ void render_depth(float *points3d_polar, unsigned int * depth_render)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int w = gridDim.x * TILE_DIM;
|
||||
int h = w /2;
|
||||
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS)
|
||||
{
|
||||
int iw = x;
|
||||
int ih = y + j;
|
||||
int tx = round((points3d_polar[(ih * w + iw) * 3 + 1] + M_PI)/(2*M_PI) * w - 0.5);
|
||||
int ty = round((points3d_polar[(ih * w + iw) * 3 + 2])/M_PI * h - 0.5);
|
||||
int this_depth = (int)(512 * points3d_polar[(ih * w + iw) * 3 + 0]);
|
||||
atomicMin(&depth_render[(ty * w + tx)] , this_depth);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
__global__ void render_final(float *points3d_polar, int * depth_render, int * img, int * render)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int w = gridDim.x * TILE_DIM;
|
||||
int h = w /2;
|
||||
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS)
|
||||
{
|
||||
int iw = x;
|
||||
int ih = y + j;
|
||||
int tx = round((points3d_polar[(ih * w + iw) * 3 + 1] + M_PI)/(2*M_PI) * w - 0.5);
|
||||
int ty = round((points3d_polar[(ih * w + iw) * 3 + 2])/M_PI * h - 0.5);
|
||||
int this_depth = (int)(12800/128 * points3d_polar[(ih * w + iw) * 3 + 0]);
|
||||
int delta = this_depth - depth_render[(ty * w + tx)];
|
||||
|
||||
//printf("%d %d\n", this_depth, depth_render[(ty * w + tx)]);
|
||||
if ((y > h/8) && (y < h*7/8))
|
||||
if ((delta > -10) && (delta < 10) && (this_depth < 10000)) {
|
||||
render[(ty * w + tx)] = img[(ih * w + iw)];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
__global__ void projectCubeMapToERImage(float *dst, float * src, uint * idxs, size_t count)
|
||||
{
|
||||
int n_to_do = count / ( gridDim.x * blockDim.x);
|
||||
int start = (blockIdx.x * blockDim.x + threadIdx.x) * n_to_do;
|
||||
//printf("x: %d w: %d | %d %d (%d)(%d)\n", blockIdx.x, threadIdx.x, gridDim.x, blockDim.x, start, n_to_do);
|
||||
for (int j = 0; j < n_to_do; j++)
|
||||
{
|
||||
dst[start + j] = src[idxs[start + j]];
|
||||
}
|
||||
}
|
||||
|
||||
__global__ void readTextureToCubeMapBuffer(float * dst, size_t width, size_t height)
|
||||
{
|
||||
unsigned int n_to_do = height * width / (blockDim.x * gridDim.x);
|
||||
int start = (blockIdx.x * blockDim.x + threadIdx.x) * n_to_do;
|
||||
// printf("Block (%i) thread (%i); n_to_do (%d); start (%d) | (%d, %d)\n",
|
||||
// blockIdx.x, threadIdx.x ,
|
||||
// n_to_do,
|
||||
// start, width, height);
|
||||
for (int j = start; j < start + n_to_do; j++)
|
||||
{
|
||||
int x_val = (j%width);
|
||||
int y_val = (j/width);
|
||||
float4 temp = tex2D(inTex, x_val, y_val); ;
|
||||
dst[j] = temp.z;
|
||||
}
|
||||
// printf("DONE (%i, %i);\n", blockIdx.x, threadIdx.x);
|
||||
}
|
||||
|
||||
|
||||
|
||||
extern "C"{
|
||||
|
||||
/* Convenience function to print any GPU errors */
|
||||
#define checkCudaErrors(ans) { gpuAssert((ans), __FILE__, __LINE__); }
|
||||
inline void gpuAssert(cudaError_t code, const char *file, int line, bool abort=true)
|
||||
{
|
||||
if (code != cudaSuccess)
|
||||
{
|
||||
fprintf(stderr,"GPUassert: %s %s %d\n", cudaGetErrorString(code), file, line);
|
||||
if (abort) exit(code);
|
||||
}
|
||||
}
|
||||
|
||||
float * allocateBufferOnGPU(size_t count)
|
||||
{
|
||||
float *d_dst;
|
||||
const int dst_mem_size = count*sizeof(float);
|
||||
cudaMalloc((void **)&d_dst, dst_mem_size);
|
||||
return d_dst;
|
||||
}
|
||||
|
||||
void projectCubeMapToEquirectangular(float * dst, float * d_src, uint *d_idx, size_t count, size_t src_size)
|
||||
{
|
||||
/* First call "d_idx = moveToGPU(cubeIdxToEqui, count)" */
|
||||
|
||||
// Declare vars
|
||||
const int dstMemSize = count*sizeof(float);
|
||||
float *d_dst;
|
||||
|
||||
// Create buffer for the equirectangular img on gpu
|
||||
cudaMalloc((void **)&d_dst, dstMemSize);
|
||||
cudaMemcpy(d_dst, dst, dstMemSize, cudaMemcpyHostToDevice);
|
||||
|
||||
// Do cube -> equirecangular projection
|
||||
projectCubeMapToERImage<<< N_BLOCKS, N_THREADS >>>(d_dst, d_src, d_idx, count);
|
||||
|
||||
// Copy back to cpu
|
||||
cudaMemcpy(dst, d_dst, dstMemSize, cudaMemcpyDeviceToHost);
|
||||
|
||||
cudaFree(d_dst);
|
||||
cudaDeviceSynchronize();
|
||||
}
|
||||
|
||||
void fillBlue(float * dst, cudaArray_t src, size_t offset, size_t w, size_t h)
|
||||
{
|
||||
/* Fills the buffer at *dst with the contents at src + offset (a h x w texture)*/
|
||||
// --- Dims
|
||||
dim3 dimBlock(N_BLOCKS);
|
||||
dim3 dimGrid(N_THREADS);
|
||||
cudaChannelFormatDesc channelDesc = cudaCreateChannelDesc(32, 32, 32, 32, cudaChannelFormatKindFloat);
|
||||
// Set the texture parameters
|
||||
inTex.normalized = false;
|
||||
cudaBindTextureToArray(inTex, src, channelDesc);
|
||||
readTextureToCubeMapBuffer<<< dimBlock, dimGrid >>>(dst + offset, w, h);
|
||||
}
|
||||
|
||||
uint * copyToGPU(uint * cubeMapIdxToEqui, size_t count)
|
||||
{
|
||||
/* Copies the given array to device */
|
||||
uint *d_idx;
|
||||
const int idxsMemSize = count*sizeof(uint);
|
||||
cudaMalloc((void **)&d_idx, idxsMemSize);
|
||||
cudaMemcpy(d_idx, cubeMapIdxToEqui, idxsMemSize, cudaMemcpyHostToDevice);
|
||||
return d_idx;
|
||||
}
|
||||
|
||||
void render(int h,int w,unsigned char * img, float * depth,float * pose, unsigned char * render, int * depth_render)
|
||||
{
|
||||
//int ih, iw, i, ic;
|
||||
|
||||
const int nx = w;
|
||||
const int ny = h;
|
||||
const int depth_mem_size = nx*ny*sizeof(float);
|
||||
const int frame_mem_size = nx*ny*sizeof(unsigned char) * 3;
|
||||
|
||||
dim3 dimGrid(nx/TILE_DIM, ny/TILE_DIM, 1);
|
||||
dim3 dimBlock(TILE_DIM, BLOCK_ROWS, 1);
|
||||
|
||||
unsigned char *d_img, *d_render;
|
||||
float *d_depth, *d_pose;
|
||||
int *d_depth_render;
|
||||
float *d_3dpoint, *d_3dpoint_after, *d_3dpoint_polar;
|
||||
|
||||
int *d_render2, *d_img2;
|
||||
|
||||
cudaMalloc((void **)&d_img, frame_mem_size);
|
||||
cudaMalloc((void **)&d_render, frame_mem_size);
|
||||
cudaMalloc((void **)&d_depth, depth_mem_size);
|
||||
cudaMalloc((void **)&d_depth_render, nx * ny * sizeof(int));
|
||||
cudaMalloc((void **)&d_3dpoint, depth_mem_size * 4);
|
||||
cudaMalloc((void **)&d_3dpoint_after, depth_mem_size * 4);
|
||||
cudaMalloc((void **)&d_3dpoint_polar, depth_mem_size * 4);
|
||||
cudaMalloc((void **)&d_pose, sizeof(float) * 16);
|
||||
cudaMalloc((void **)&d_render2, nx * ny * sizeof(int));
|
||||
cudaMalloc((void **)&d_img2, nx * ny * sizeof(int));
|
||||
|
||||
cudaMemcpy(d_depth_render, depth_render, nx * ny * sizeof(int), cudaMemcpyHostToDevice);
|
||||
cudaMemcpy(d_pose, pose, sizeof(float) * 16, cudaMemcpyHostToDevice);
|
||||
cudaMemcpy(d_img, img, frame_mem_size, cudaMemcpyHostToDevice);
|
||||
cudaMemcpy(d_depth, depth, depth_mem_size, cudaMemcpyHostToDevice);
|
||||
cudaMemcpy(d_render, render, frame_mem_size, cudaMemcpyHostToDevice);
|
||||
|
||||
cudaMemset(d_render2, 0, nx * ny * sizeof(int));
|
||||
cudaMemset(d_img2, 0, nx * ny * sizeof(int));
|
||||
|
||||
cudaMemset(d_3dpoint, 0, depth_mem_size * 4);
|
||||
cudaMemset(d_3dpoint_after, 0, depth_mem_size * 4);
|
||||
|
||||
to3d_point<<< dimGrid, dimBlock >>>(d_depth, d_3dpoint);
|
||||
transform<<< dimGrid, dimBlock >>>(d_3dpoint_after, d_3dpoint, d_pose);
|
||||
transform2d<<<dimGrid, dimBlock>>>(d_3dpoint_after, d_3dpoint_polar);
|
||||
|
||||
char_to_int <<< dimGrid, dimBlock >>> (d_img2, d_img);
|
||||
char_to_int <<< dimGrid, dimBlock >>> (d_render2, d_render);
|
||||
|
||||
//render_depth <<< dimGrid, dimBlock >>> (d_3dpoint_polar, d_depth_render);
|
||||
render_final <<< dimGrid, dimBlock >>> (d_3dpoint_polar, d_depth_render, d_img2, d_render2);
|
||||
|
||||
int_to_char <<< dimGrid, dimBlock >>> (d_render2, d_render);
|
||||
|
||||
cudaMemcpy(render, d_render, frame_mem_size, cudaMemcpyDeviceToHost);
|
||||
//cudaMemcpy(depth_render, d_depth_render, nx * ny * sizeof(unsigned int), cudaMemcpyDeviceToHost);
|
||||
|
||||
cudaFree(d_img);
|
||||
cudaFree(d_depth);
|
||||
cudaFree(d_render2);
|
||||
cudaFree(d_img2);
|
||||
cudaFree(d_render);
|
||||
cudaFree(d_depth_render);
|
||||
cudaFree(d_3dpoint);
|
||||
cudaFree(d_3dpoint_after);
|
||||
cudaFree(d_3dpoint_polar);
|
||||
cudaFree(d_pose);
|
||||
}
|
||||
|
||||
}//extern "C"
|
|
@ -1,12 +0,0 @@
|
|||
#ifndef RENDER_CUDA_F_HPP
|
||||
#define RENDER_CUDA_F_HPP
|
||||
|
||||
|
||||
extern "C" {
|
||||
uint* copyToGPU(uint * cube_idx_to_equi, size_t count);
|
||||
void projectCubeMapToEquirectangular(float * dst, float * src, uint * cube_idx_to_equi, size_t count, size_t src_size);
|
||||
float* allocateBufferOnGPU(size_t count);
|
||||
void fillBlue(float * dst, cudaArray_t src, size_t offset, size_t w, size_t h);
|
||||
}
|
||||
|
||||
#endif
|
|
@ -1,78 +0,0 @@
|
|||
#ifndef SEMANTIC_COLOR_HPP
|
||||
#define SEMANTIC_COLOR_HPP
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <vector>
|
||||
#include <cstdlib> //rand
|
||||
#include <GL/glut.h>
|
||||
#include <fstream>
|
||||
#include <glfw3.h>
|
||||
#include "common/MTLtexture.hpp"
|
||||
#include <algorithm>
|
||||
|
||||
std::map<std::string, std::vector<unsigned char>> color_map_2d3ds = {
|
||||
{ "<UNK>", {0, 0, 0} },
|
||||
{ "ceiling", {241, 255, 82} },
|
||||
{ "floor", {102, 168, 226} },
|
||||
{ "window", {0, 255, 0} },
|
||||
{ "door", {113, 143, 65} },
|
||||
{ "column", {89, 173, 163} },
|
||||
{ "beam", {254, 158, 137} },
|
||||
{ "wall", {190, 123, 75} },
|
||||
{ "sofa", {100, 22, 116} },
|
||||
{ "chair", {0, 18, 141} },
|
||||
{ "table", {84, 84, 84} },
|
||||
{ "board", {85, 116, 127} },
|
||||
{ "bookcase", {255, 31, 33} },
|
||||
{ "clutter", {228, 228, 228} },
|
||||
};
|
||||
|
||||
|
||||
void color_coding_RAND (GLubyte color[]) {
|
||||
color[0] = (unsigned char) (rand()%255);
|
||||
color[1] = (unsigned char) (rand()%255);
|
||||
color[2] = (unsigned char) (rand()%255);
|
||||
};
|
||||
|
||||
|
||||
void color_coding_2D3DS (GLubyte color[], unsigned int id) {
|
||||
/* Parse a 24-bit integer as a RGB color. I.e. Convert to base 256
|
||||
Adapted from alexsax/2D-3D-Semantics
|
||||
Args:
|
||||
index: An int. The first 24 bits will be interpreted as a color.
|
||||
Negative values will not work properly.
|
||||
Returns:
|
||||
color: A color s.t. get_index( get_color( i ) ) = i
|
||||
*/
|
||||
unsigned char b = ( id ) % 256; // least significant byte
|
||||
unsigned char g = ( id >> 8 ) % 256;
|
||||
unsigned char r = ( id >> 16 ) % 256; // most significant byte
|
||||
color[0] = r;
|
||||
color[1] = g;
|
||||
color[2] = b;
|
||||
};
|
||||
|
||||
|
||||
void color_coding_MP3D (GLubyte color[], unsigned int id) {
|
||||
unsigned char b = ( id ) % 256; // least significant byte
|
||||
unsigned char g = ( id >> 8 ) % 256;
|
||||
unsigned char r = ( id >> 16 ) % 256; // most significant byte
|
||||
color[0] = r;
|
||||
color[1] = g;
|
||||
color[2] = b;
|
||||
};
|
||||
|
||||
|
||||
void color_coding_2D3DS_pretty (GLubyte color[], std::string name) {
|
||||
/* Color code 2D3DS semantics in a nice pretty way
|
||||
*/
|
||||
std::string name_prefix = name.substr(0, name.find("_", 0));
|
||||
std::vector<unsigned char> assign_color = color_map_2d3ds.find(name_prefix)->second;
|
||||
color[0] = assign_color[0];
|
||||
color[1] = assign_color[1];
|
||||
color[2] = assign_color[2];
|
||||
};
|
||||
|
||||
#endif
|
|
@ -1,110 +0,0 @@
|
|||
#include <stdio.h>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include <iostream>
|
||||
#include <fstream>
|
||||
#include <algorithm>
|
||||
using namespace std;
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
//#include <GL/glew.h>
|
||||
#include <glad/gl.h>
|
||||
#include "shader.hpp"
|
||||
|
||||
GLuint LoadShaders(const char * vertex_file_path,const char * fragment_file_path){
|
||||
|
||||
// Create the shaders
|
||||
GLuint VertexShaderID = glCreateShader(GL_VERTEX_SHADER);
|
||||
GLuint FragmentShaderID = glCreateShader(GL_FRAGMENT_SHADER);
|
||||
|
||||
// Read the Vertex Shader code from the file
|
||||
std::string VertexShaderCode;
|
||||
std::ifstream VertexShaderStream(vertex_file_path, std::ios::in);
|
||||
if(VertexShaderStream.is_open()){
|
||||
std::string Line = "";
|
||||
while(getline(VertexShaderStream, Line))
|
||||
VertexShaderCode += "\n" + Line;
|
||||
VertexShaderStream.close();
|
||||
}else{
|
||||
printf("Impossible to open %s. Are you in the right directory ? Don't forget to read the FAQ !\n", vertex_file_path);
|
||||
getchar();
|
||||
return 0;
|
||||
}
|
||||
|
||||
// Read the Fragment Shader code from the file
|
||||
std::string FragmentShaderCode;
|
||||
std::ifstream FragmentShaderStream(fragment_file_path, std::ios::in);
|
||||
if(FragmentShaderStream.is_open()){
|
||||
std::string Line = "";
|
||||
while(getline(FragmentShaderStream, Line))
|
||||
FragmentShaderCode += "\n" + Line;
|
||||
FragmentShaderStream.close();
|
||||
}
|
||||
|
||||
GLint Result = GL_FALSE;
|
||||
int InfoLogLength;
|
||||
|
||||
|
||||
// Compile Vertex Shader
|
||||
// printf("Compiling shader : %s\n", vertex_file_path);
|
||||
char const * VertexSourcePointer = VertexShaderCode.c_str();
|
||||
glShaderSource(VertexShaderID, 1, &VertexSourcePointer , NULL);
|
||||
glCompileShader(VertexShaderID);
|
||||
|
||||
// Check Vertex Shader
|
||||
glGetShaderiv(VertexShaderID, GL_COMPILE_STATUS, &Result);
|
||||
glGetShaderiv(VertexShaderID, GL_INFO_LOG_LENGTH, &InfoLogLength);
|
||||
if ( InfoLogLength > 0 ){
|
||||
std::vector<char> VertexShaderErrorMessage(InfoLogLength+1);
|
||||
glGetShaderInfoLog(VertexShaderID, InfoLogLength, NULL, &VertexShaderErrorMessage[0]);
|
||||
printf("%s\n", &VertexShaderErrorMessage[0]);
|
||||
}
|
||||
|
||||
|
||||
|
||||
// Compile Fragment Shader
|
||||
// printf("Compiling shader : %s\n", fragment_file_path);
|
||||
char const * FragmentSourcePointer = FragmentShaderCode.c_str();
|
||||
glShaderSource(FragmentShaderID, 1, &FragmentSourcePointer , NULL);
|
||||
glCompileShader(FragmentShaderID);
|
||||
|
||||
// Check Fragment Shader
|
||||
glGetShaderiv(FragmentShaderID, GL_COMPILE_STATUS, &Result);
|
||||
glGetShaderiv(FragmentShaderID, GL_INFO_LOG_LENGTH, &InfoLogLength);
|
||||
if ( InfoLogLength > 0 ){
|
||||
std::vector<char> FragmentShaderErrorMessage(InfoLogLength+1);
|
||||
glGetShaderInfoLog(FragmentShaderID, InfoLogLength, NULL, &FragmentShaderErrorMessage[0]);
|
||||
printf("%s\n", &FragmentShaderErrorMessage[0]);
|
||||
}
|
||||
|
||||
|
||||
|
||||
// Link the program
|
||||
// printf("Linking program\n");
|
||||
GLuint ProgramID = glCreateProgram();
|
||||
glAttachShader(ProgramID, VertexShaderID);
|
||||
glAttachShader(ProgramID, FragmentShaderID);
|
||||
glLinkProgram(ProgramID);
|
||||
|
||||
// Check the program
|
||||
glGetProgramiv(ProgramID, GL_LINK_STATUS, &Result);
|
||||
glGetProgramiv(ProgramID, GL_INFO_LOG_LENGTH, &InfoLogLength);
|
||||
if ( InfoLogLength > 0 ){
|
||||
std::vector<char> ProgramErrorMessage(InfoLogLength+1);
|
||||
glGetProgramInfoLog(ProgramID, InfoLogLength, NULL, &ProgramErrorMessage[0]);
|
||||
printf("%s\n", &ProgramErrorMessage[0]);
|
||||
}
|
||||
|
||||
|
||||
glDetachShader(ProgramID, VertexShaderID);
|
||||
glDetachShader(ProgramID, FragmentShaderID);
|
||||
|
||||
glDeleteShader(VertexShaderID);
|
||||
glDeleteShader(FragmentShaderID);
|
||||
|
||||
return ProgramID;
|
||||
}
|
||||
|
||||
|
|
@ -1,6 +0,0 @@
|
|||
#ifndef SHADER_HPP
|
||||
#define SHADER_HPP
|
||||
|
||||
GLuint LoadShaders(const char * vertex_file_path,const char * fragment_file_path);
|
||||
|
||||
#endif
|
|
@ -1,73 +0,0 @@
|
|||
#include <vector>
|
||||
#include <glm/glm.hpp>
|
||||
|
||||
#include "tangentspace.hpp"
|
||||
|
||||
void computeTangentBasis(
|
||||
// inputs
|
||||
std::vector<glm::vec3> & vertices,
|
||||
std::vector<glm::vec2> & uvs,
|
||||
std::vector<glm::vec3> & normals,
|
||||
// outputs
|
||||
std::vector<glm::vec3> & tangents,
|
||||
std::vector<glm::vec3> & bitangents
|
||||
){
|
||||
|
||||
for (unsigned int i=0; i<vertices.size(); i+=3 ){
|
||||
|
||||
// Shortcuts for vertices
|
||||
glm::vec3 & v0 = vertices[i+0];
|
||||
glm::vec3 & v1 = vertices[i+1];
|
||||
glm::vec3 & v2 = vertices[i+2];
|
||||
|
||||
// Shortcuts for UVs
|
||||
glm::vec2 & uv0 = uvs[i+0];
|
||||
glm::vec2 & uv1 = uvs[i+1];
|
||||
glm::vec2 & uv2 = uvs[i+2];
|
||||
|
||||
// Edges of the triangle : postion delta
|
||||
glm::vec3 deltaPos1 = v1-v0;
|
||||
glm::vec3 deltaPos2 = v2-v0;
|
||||
|
||||
// UV delta
|
||||
glm::vec2 deltaUV1 = uv1-uv0;
|
||||
glm::vec2 deltaUV2 = uv2-uv0;
|
||||
|
||||
float r = 1.0f / (deltaUV1.x * deltaUV2.y - deltaUV1.y * deltaUV2.x);
|
||||
glm::vec3 tangent = (deltaPos1 * deltaUV2.y - deltaPos2 * deltaUV1.y)*r;
|
||||
glm::vec3 bitangent = (deltaPos2 * deltaUV1.x - deltaPos1 * deltaUV2.x)*r;
|
||||
|
||||
// Set the same tangent for all three vertices of the triangle.
|
||||
// They will be merged later, in vboindexer.cpp
|
||||
tangents.push_back(tangent);
|
||||
tangents.push_back(tangent);
|
||||
tangents.push_back(tangent);
|
||||
|
||||
// Same thing for binormals
|
||||
bitangents.push_back(bitangent);
|
||||
bitangents.push_back(bitangent);
|
||||
bitangents.push_back(bitangent);
|
||||
|
||||
}
|
||||
|
||||
// See "Going Further"
|
||||
for (unsigned int i=0; i<vertices.size(); i+=1 )
|
||||
{
|
||||
glm::vec3 & n = normals[i];
|
||||
glm::vec3 & t = tangents[i];
|
||||
glm::vec3 & b = bitangents[i];
|
||||
|
||||
// Gram-Schmidt orthogonalize
|
||||
t = glm::normalize(t - n * glm::dot(n, t));
|
||||
|
||||
// Calculate handedness
|
||||
if (glm::dot(glm::cross(n, t), b) < 0.0f){
|
||||
t = t * -1.0f;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
|
@ -1,15 +0,0 @@
|
|||
#ifndef TANGENTSPACE_HPP
|
||||
#define TANGENTSPACE_HPP
|
||||
|
||||
void computeTangentBasis(
|
||||
// inputs
|
||||
std::vector<glm::vec3> & vertices,
|
||||
std::vector<glm::vec2> & uvs,
|
||||
std::vector<glm::vec3> & normals,
|
||||
// outputs
|
||||
std::vector<glm::vec3> & tangents,
|
||||
std::vector<glm::vec3> & bitangents
|
||||
);
|
||||
|
||||
|
||||
#endif
|
|
@ -1,124 +0,0 @@
|
|||
#include <vector>
|
||||
#include <cstring>
|
||||
|
||||
#include <GL/glew.h>
|
||||
|
||||
#include <glm/glm.hpp>
|
||||
#include <glm/gtc/matrix_transform.hpp>
|
||||
using namespace glm;
|
||||
|
||||
#include "shader.hpp"
|
||||
#include "texture.hpp"
|
||||
|
||||
#include "text2D.hpp"
|
||||
|
||||
unsigned int Text2DTextureID;
|
||||
unsigned int Text2DVertexBufferID;
|
||||
unsigned int Text2DUVBufferID;
|
||||
unsigned int Text2DShaderID;
|
||||
unsigned int Text2DUniformID;
|
||||
|
||||
void initText2D(const char * texturePath){
|
||||
|
||||
// Initialize texture
|
||||
Text2DTextureID = loadDDS(texturePath);
|
||||
|
||||
// Initialize VBO
|
||||
glGenBuffers(1, &Text2DVertexBufferID);
|
||||
glGenBuffers(1, &Text2DUVBufferID);
|
||||
|
||||
// Initialize Shader
|
||||
Text2DShaderID = LoadShaders( "TextVertexShader.vertexshader", "TextVertexShader.fragmentshader" );
|
||||
|
||||
// Initialize uniforms' IDs
|
||||
Text2DUniformID = glGetUniformLocation( Text2DShaderID, "myTextureSampler" );
|
||||
|
||||
}
|
||||
|
||||
void printText2D(const char * text, int x, int y, int size){
|
||||
|
||||
unsigned int length = strlen(text);
|
||||
|
||||
// Fill buffers
|
||||
std::vector<glm::vec2> vertices;
|
||||
std::vector<glm::vec2> UVs;
|
||||
for ( unsigned int i=0 ; i<length ; i++ ){
|
||||
|
||||
glm::vec2 vertex_up_left = glm::vec2( x+i*size , y+size );
|
||||
glm::vec2 vertex_up_right = glm::vec2( x+i*size+size, y+size );
|
||||
glm::vec2 vertex_down_right = glm::vec2( x+i*size+size, y );
|
||||
glm::vec2 vertex_down_left = glm::vec2( x+i*size , y );
|
||||
|
||||
vertices.push_back(vertex_up_left );
|
||||
vertices.push_back(vertex_down_left );
|
||||
vertices.push_back(vertex_up_right );
|
||||
|
||||
vertices.push_back(vertex_down_right);
|
||||
vertices.push_back(vertex_up_right);
|
||||
vertices.push_back(vertex_down_left);
|
||||
|
||||
char character = text[i];
|
||||
float uv_x = (character%16)/16.0f;
|
||||
float uv_y = (character/16)/16.0f;
|
||||
|
||||
glm::vec2 uv_up_left = glm::vec2( uv_x , uv_y );
|
||||
glm::vec2 uv_up_right = glm::vec2( uv_x+1.0f/16.0f, uv_y );
|
||||
glm::vec2 uv_down_right = glm::vec2( uv_x+1.0f/16.0f, (uv_y + 1.0f/16.0f) );
|
||||
glm::vec2 uv_down_left = glm::vec2( uv_x , (uv_y + 1.0f/16.0f) );
|
||||
UVs.push_back(uv_up_left );
|
||||
UVs.push_back(uv_down_left );
|
||||
UVs.push_back(uv_up_right );
|
||||
|
||||
UVs.push_back(uv_down_right);
|
||||
UVs.push_back(uv_up_right);
|
||||
UVs.push_back(uv_down_left);
|
||||
}
|
||||
glBindBuffer(GL_ARRAY_BUFFER, Text2DVertexBufferID);
|
||||
glBufferData(GL_ARRAY_BUFFER, vertices.size() * sizeof(glm::vec2), &vertices[0], GL_STATIC_DRAW);
|
||||
glBindBuffer(GL_ARRAY_BUFFER, Text2DUVBufferID);
|
||||
glBufferData(GL_ARRAY_BUFFER, UVs.size() * sizeof(glm::vec2), &UVs[0], GL_STATIC_DRAW);
|
||||
|
||||
// Bind shader
|
||||
glUseProgram(Text2DShaderID);
|
||||
|
||||
// Bind texture
|
||||
glActiveTexture(GL_TEXTURE0);
|
||||
glBindTexture(GL_TEXTURE_2D, Text2DTextureID);
|
||||
// Set our "myTextureSampler" sampler to use Texture Unit 0
|
||||
glUniform1i(Text2DUniformID, 0);
|
||||
|
||||
// 1rst attribute buffer : vertices
|
||||
glEnableVertexAttribArray(0);
|
||||
glBindBuffer(GL_ARRAY_BUFFER, Text2DVertexBufferID);
|
||||
glVertexAttribPointer(0, 2, GL_FLOAT, GL_FALSE, 0, (void*)0 );
|
||||
|
||||
// 2nd attribute buffer : UVs
|
||||
glEnableVertexAttribArray(1);
|
||||
glBindBuffer(GL_ARRAY_BUFFER, Text2DUVBufferID);
|
||||
glVertexAttribPointer(1, 2, GL_FLOAT, GL_FALSE, 0, (void*)0 );
|
||||
|
||||
glEnable(GL_BLEND);
|
||||
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
|
||||
|
||||
// Draw call
|
||||
glDrawArrays(GL_TRIANGLES, 0, vertices.size() );
|
||||
|
||||
glDisable(GL_BLEND);
|
||||
|
||||
glDisableVertexAttribArray(0);
|
||||
glDisableVertexAttribArray(1);
|
||||
|
||||
}
|
||||
|
||||
void cleanupText2D(){
|
||||
|
||||
// Delete buffers
|
||||
glDeleteBuffers(1, &Text2DVertexBufferID);
|
||||
glDeleteBuffers(1, &Text2DUVBufferID);
|
||||
|
||||
// Delete texture
|
||||
glDeleteTextures(1, &Text2DTextureID);
|
||||
|
||||
// Delete shader
|
||||
glDeleteProgram(Text2DShaderID);
|
||||
}
|
|
@ -1,8 +0,0 @@
|
|||
#ifndef TEXT2D_HPP
|
||||
#define TEXT2D_HPP
|
||||
|
||||
void initText2D(const char * texturePath);
|
||||
void printText2D(const char * text, int x, int y, int size);
|
||||
void cleanupText2D();
|
||||
|
||||
#endif
|
|
@ -1,218 +0,0 @@
|
|||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#include <GL/glew.h>
|
||||
|
||||
#include <glfw3.h>
|
||||
|
||||
|
||||
GLuint loadBMP_custom(const char * imagepath){
|
||||
|
||||
printf("Reading image %s\n", imagepath);
|
||||
|
||||
// Data read from the header of the BMP file
|
||||
unsigned char header[54];
|
||||
unsigned int dataPos;
|
||||
unsigned int imageSize;
|
||||
unsigned int width, height;
|
||||
// Actual RGB data
|
||||
unsigned char * data;
|
||||
|
||||
// Open the file
|
||||
FILE * file = fopen(imagepath,"rb");
|
||||
if (!file){
|
||||
printf("%s could not be opened. Are you in the right directory ? Don't forget to read the FAQ !\n", imagepath);
|
||||
getchar();
|
||||
return 0;
|
||||
}
|
||||
|
||||
// Read the header, i.e. the 54 first bytes
|
||||
|
||||
// If less than 54 bytes are read, problem
|
||||
if ( fread(header, 1, 54, file)!=54 ){
|
||||
printf("Not a correct BMP file\n");
|
||||
fclose(file);
|
||||
return 0;
|
||||
}
|
||||
// A BMP files always begins with "BM"
|
||||
if ( header[0]!='B' || header[1]!='M' ){
|
||||
printf("Not a correct BMP file\n");
|
||||
fclose(file);
|
||||
return 0;
|
||||
}
|
||||
// Make sure this is a 24bpp file
|
||||
if ( *(int*)&(header[0x1E])!=0 ) {printf("Not a correct BMP file\n"); fclose(file); return 0;}
|
||||
if ( *(int*)&(header[0x1C])!=24 ) {printf("Not a correct BMP file\n"); fclose(file); return 0;}
|
||||
|
||||
// Read the information about the image
|
||||
dataPos = *(int*)&(header[0x0A]);
|
||||
imageSize = *(int*)&(header[0x22]);
|
||||
width = *(int*)&(header[0x12]);
|
||||
height = *(int*)&(header[0x16]);
|
||||
|
||||
// Some BMP files are misformatted, guess missing information
|
||||
if (imageSize==0) imageSize=width*height*3; // 3 : one byte for each Red, Green and Blue component
|
||||
if (dataPos==0) dataPos=54; // The BMP header is done that way
|
||||
|
||||
// Create a buffer
|
||||
data = new unsigned char [imageSize];
|
||||
|
||||
// Read the actual data from the file into the buffer
|
||||
fread(data,1,imageSize,file);
|
||||
|
||||
// Everything is in memory now, the file can be closed.
|
||||
fclose (file);
|
||||
|
||||
// Create one OpenGL texture
|
||||
GLuint textureID;
|
||||
glGenTextures(1, &textureID);
|
||||
|
||||
// "Bind" the newly created texture : all future texture functions will modify this texture
|
||||
glBindTexture(GL_TEXTURE_2D, textureID);
|
||||
|
||||
// Give the image to OpenGL
|
||||
glTexImage2D(GL_TEXTURE_2D, 0,GL_RGB, width, height, 0, GL_BGR, GL_UNSIGNED_BYTE, data);
|
||||
|
||||
// OpenGL has now copied the data. Free our own version
|
||||
delete [] data;
|
||||
|
||||
// Poor filtering, or ...
|
||||
//glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
|
||||
//glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
|
||||
|
||||
// ... nice trilinear filtering ...
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR);
|
||||
// ... which requires mipmaps. Generate them automatically.
|
||||
glGenerateMipmap(GL_TEXTURE_2D);
|
||||
|
||||
// Return the ID of the texture we just created
|
||||
return textureID;
|
||||
}
|
||||
|
||||
// Since GLFW 3, glfwLoadTexture2D() has been removed. You have to use another texture loading library,
|
||||
// or do it yourself (just like loadBMP_custom and loadDDS)
|
||||
//GLuint loadTGA_glfw(const char * imagepath){
|
||||
//
|
||||
// // Create one OpenGL texture
|
||||
// GLuint textureID;
|
||||
// glGenTextures(1, &textureID);
|
||||
//
|
||||
// // "Bind" the newly created texture : all future texture functions will modify this texture
|
||||
// glBindTexture(GL_TEXTURE_2D, textureID);
|
||||
//
|
||||
// // Read the file, call glTexImage2D with the right parameters
|
||||
// glfwLoadTexture2D(imagepath, 0);
|
||||
//
|
||||
// // Nice trilinear filtering.
|
||||
// glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
|
||||
// glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
|
||||
// glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
|
||||
// glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR);
|
||||
// glGenerateMipmap(GL_TEXTURE_2D);
|
||||
//
|
||||
// // Return the ID of the texture we just created
|
||||
// return textureID;
|
||||
//}
|
||||
|
||||
|
||||
|
||||
#define FOURCC_DXT1 0x31545844 // Equivalent to "DXT1" in ASCII
|
||||
#define FOURCC_DXT3 0x33545844 // Equivalent to "DXT3" in ASCII
|
||||
#define FOURCC_DXT5 0x35545844 // Equivalent to "DXT5" in ASCII
|
||||
|
||||
GLuint loadDDS(const char * imagepath){
|
||||
|
||||
unsigned char header[124];
|
||||
|
||||
FILE *fp;
|
||||
|
||||
/* try to open the file */
|
||||
fp = fopen(imagepath, "rb");
|
||||
if (fp == NULL){
|
||||
printf("%s could not be opened. Are you in the right directory ? Don't forget to read the FAQ !\n", imagepath); getchar();
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* verify the type of file */
|
||||
char filecode[4];
|
||||
fread(filecode, 1, 4, fp);
|
||||
if (strncmp(filecode, "DDS ", 4) != 0) {
|
||||
fclose(fp);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* get the surface desc */
|
||||
fread(&header, 124, 1, fp);
|
||||
|
||||
unsigned int height = *(unsigned int*)&(header[8 ]);
|
||||
unsigned int width = *(unsigned int*)&(header[12]);
|
||||
unsigned int linearSize = *(unsigned int*)&(header[16]);
|
||||
unsigned int mipMapCount = *(unsigned int*)&(header[24]);
|
||||
unsigned int fourCC = *(unsigned int*)&(header[80]);
|
||||
|
||||
|
||||
unsigned char * buffer;
|
||||
unsigned int bufsize;
|
||||
/* how big is it going to be including all mipmaps? */
|
||||
bufsize = mipMapCount > 1 ? linearSize * 2 : linearSize;
|
||||
buffer = (unsigned char*)malloc(bufsize * sizeof(unsigned char));
|
||||
fread(buffer, 1, bufsize, fp);
|
||||
/* close the file pointer */
|
||||
fclose(fp);
|
||||
|
||||
unsigned int components = (fourCC == FOURCC_DXT1) ? 3 : 4;
|
||||
unsigned int format;
|
||||
switch(fourCC)
|
||||
{
|
||||
case FOURCC_DXT1:
|
||||
format = GL_COMPRESSED_RGBA_S3TC_DXT1_EXT;
|
||||
break;
|
||||
case FOURCC_DXT3:
|
||||
format = GL_COMPRESSED_RGBA_S3TC_DXT3_EXT;
|
||||
break;
|
||||
case FOURCC_DXT5:
|
||||
format = GL_COMPRESSED_RGBA_S3TC_DXT5_EXT;
|
||||
break;
|
||||
default:
|
||||
free(buffer);
|
||||
return 0;
|
||||
}
|
||||
|
||||
// Create one OpenGL texture
|
||||
GLuint textureID;
|
||||
glGenTextures(1, &textureID);
|
||||
|
||||
// "Bind" the newly created texture : all future texture functions will modify this texture
|
||||
glBindTexture(GL_TEXTURE_2D, textureID);
|
||||
glPixelStorei(GL_UNPACK_ALIGNMENT,1);
|
||||
|
||||
unsigned int blockSize = (format == GL_COMPRESSED_RGBA_S3TC_DXT1_EXT) ? 8 : 16;
|
||||
unsigned int offset = 0;
|
||||
|
||||
/* load the mipmaps */
|
||||
for (unsigned int level = 0; level < mipMapCount && (width || height); ++level)
|
||||
{
|
||||
unsigned int size = ((width+3)/4)*((height+3)/4)*blockSize;
|
||||
glCompressedTexImage2D(GL_TEXTURE_2D, level, format, width, height,
|
||||
0, size, buffer + offset);
|
||||
|
||||
offset += size;
|
||||
width /= 2;
|
||||
height /= 2;
|
||||
|
||||
// Deal with Non-Power-Of-Two textures. This code is not included in the webpage to reduce clutter.
|
||||
if(width < 1) width = 1;
|
||||
if(height < 1) height = 1;
|
||||
|
||||
}
|
||||
|
||||
free(buffer);
|
||||
|
||||
return textureID;
|
||||
|
||||
|
||||
}
|
|
@ -1,16 +0,0 @@
|
|||
#ifndef TEXTURE_HPP
|
||||
#define TEXTURE_HPP
|
||||
|
||||
// Load a .BMP file using our custom loader
|
||||
GLuint loadBMP_custom(const char * imagepath);
|
||||
|
||||
//// Since GLFW 3, glfwLoadTexture2D() has been removed. You have to use another texture loading library,
|
||||
//// or do it yourself (just like loadBMP_custom and loadDDS)
|
||||
//// Load a .TGA file using GLFW's own loader
|
||||
//GLuint loadTGA_glfw(const char * imagepath);
|
||||
|
||||
// Load a .DDS file using GLFW's own loader
|
||||
GLuint loadDDS(const char * imagepath);
|
||||
|
||||
|
||||
#endif
|
|
@ -1,621 +0,0 @@
|
|||
// This software is in the public domain. Where that dedication is not
|
||||
// recognized, you are granted a perpetual, irrevocable license to copy,
|
||||
// distribute, and modify this file as you see fit.
|
||||
// Authored in 2015 by Dimitri Diakopoulos (http://www.dimitridiakopoulos.com)
|
||||
// https://github.com/ddiakopoulos/tinyply
|
||||
// Version 2.0
|
||||
|
||||
#include "tinyply.h"
|
||||
#include <algorithm>
|
||||
#include <functional>
|
||||
#include <type_traits>
|
||||
#include <iostream>
|
||||
#include <cstring>
|
||||
|
||||
using namespace tinyply;
|
||||
using namespace std;
|
||||
|
||||
//////////////////
|
||||
// Endian Utils //
|
||||
//////////////////
|
||||
|
||||
template<typename T> T endian_swap(const T & v) { return v; }
|
||||
template<> inline uint16_t endian_swap(const uint16_t & v) { return (v << 8) | (v >> 8); }
|
||||
template<> inline uint32_t endian_swap(const uint32_t & v) { return (v << 24) | ((v << 8) & 0x00ff0000) | ((v >> 8) & 0x0000ff00) | (v >> 24); }
|
||||
template<> inline uint64_t endian_swap(const uint64_t & v)
|
||||
{
|
||||
return (((v & 0x00000000000000ffLL) << 56) |
|
||||
((v & 0x000000000000ff00LL) << 40) |
|
||||
((v & 0x0000000000ff0000LL) << 24) |
|
||||
((v & 0x00000000ff000000LL) << 8) |
|
||||
((v & 0x000000ff00000000LL) >> 8) |
|
||||
((v & 0x0000ff0000000000LL) >> 24) |
|
||||
((v & 0x00ff000000000000LL) >> 40) |
|
||||
((v & 0xff00000000000000LL) >> 56));
|
||||
}
|
||||
template<> inline int16_t endian_swap(const int16_t & v) { uint16_t r = endian_swap(*(uint16_t*)&v); return *(int16_t*)&r; }
|
||||
template<> inline int32_t endian_swap(const int32_t & v) { uint32_t r = endian_swap(*(uint32_t*)&v); return *(int32_t*)&r; }
|
||||
template<> inline int64_t endian_swap(const int64_t & v) { uint64_t r = endian_swap(*(uint64_t*)&v); return *(int64_t*)&r; }
|
||||
inline float endian_swap_float(const uint32_t & v) { union { float f; uint32_t i; }; i = endian_swap(v); return f; }
|
||||
inline double endian_swap_double(const uint64_t & v) { union { double d; uint64_t i; }; i = endian_swap(v); return d; }
|
||||
|
||||
/////////////////////////////
|
||||
// Internal Implementation //
|
||||
/////////////////////////////
|
||||
|
||||
inline Type property_type_from_string(const std::string & t)
|
||||
{
|
||||
if (t == "int8" || t == "char") return Type::INT8;
|
||||
else if (t == "uint8" || t == "uchar") return Type::UINT8;
|
||||
else if (t == "int16" || t == "short") return Type::INT16;
|
||||
else if (t == "uint16" || t == "ushort") return Type::UINT16;
|
||||
else if (t == "int32" || t == "int") return Type::INT32;
|
||||
else if (t == "uint32" || t == "uint") return Type::UINT32;
|
||||
else if (t == "float32" || t == "float") return Type::FLOAT32;
|
||||
else if (t == "float64" || t == "double") return Type::FLOAT64;
|
||||
return Type::INVALID;
|
||||
}
|
||||
|
||||
struct PlyFile::PlyFileImpl
|
||||
{
|
||||
struct PlyCursor
|
||||
{
|
||||
size_t byteOffset;
|
||||
size_t totalSizeBytes;
|
||||
};
|
||||
|
||||
struct ParsingHelper
|
||||
{
|
||||
std::shared_ptr<PlyData> data;
|
||||
std::shared_ptr<PlyCursor> cursor;
|
||||
};
|
||||
|
||||
std::map<std::string, ParsingHelper> userData;
|
||||
|
||||
bool isBinary = false;
|
||||
bool isBigEndian = false;
|
||||
std::vector<PlyElement> elements;
|
||||
std::vector<std::string> comments;
|
||||
std::vector<std::string> objInfo;
|
||||
|
||||
void read(std::istream & is);
|
||||
void write(std::ostream & os, bool isBinary);
|
||||
|
||||
std::shared_ptr<PlyData> request_properties_from_element(const std::string & elementKey, const std::initializer_list<std::string> propertyKeys);
|
||||
void add_properties_to_element(const std::string & elementKey, const std::initializer_list<std::string> propertyKeys, const Type type, const size_t count, uint8_t * data, const Type listType, const size_t listCount);
|
||||
|
||||
size_t read_property_binary(const Type t, void * dest, size_t & destOffset, std::istream & is);
|
||||
size_t read_property_ascii(const Type t, void * dest, size_t & destOffset, std::istream & is);
|
||||
size_t skip_property_binary(const PlyProperty & property, std::istream & is);
|
||||
size_t skip_property_ascii(const PlyProperty & property, std::istream & is);
|
||||
|
||||
bool parse_header(std::istream & is);
|
||||
void parse_data(std::istream & is, bool firstPass);
|
||||
void read_header_format(std::istream & is);
|
||||
void read_header_element(std::istream & is);
|
||||
void read_header_property(std::istream & is);
|
||||
void read_header_text(std::string line, std::istream & is, std::vector<std::string> & place, int erase = 0);
|
||||
|
||||
void write_header(std::ostream & os);
|
||||
void write_ascii_internal(std::ostream & os);
|
||||
void write_binary_internal(std::ostream & os);
|
||||
void write_property_ascii(Type t, std::ostream & os, uint8_t * src, size_t & srcOffset);
|
||||
void write_property_binary(Type t, std::ostream & os, uint8_t * src, size_t & srcOffset);
|
||||
};
|
||||
|
||||
//////////////////
|
||||
// PLY Property //
|
||||
//////////////////
|
||||
|
||||
PlyProperty::PlyProperty(std::istream & is) : isList(false)
|
||||
{
|
||||
std::string type;
|
||||
is >> type;
|
||||
if (type == "list")
|
||||
{
|
||||
std::string countType;
|
||||
is >> countType >> type;
|
||||
listType = property_type_from_string(countType);
|
||||
isList = true;
|
||||
}
|
||||
propertyType = property_type_from_string(type);
|
||||
is >> name;
|
||||
}
|
||||
|
||||
/////////////////
|
||||
// PLY Element //
|
||||
/////////////////
|
||||
|
||||
PlyElement::PlyElement(std::istream & is)
|
||||
{
|
||||
is >> name >> size;
|
||||
}
|
||||
|
||||
///////////
|
||||
// Utils //
|
||||
///////////
|
||||
|
||||
std::string make_key(const std::string & a, const std::string & b)
|
||||
{
|
||||
return (a + "-" + b);
|
||||
}
|
||||
|
||||
template<typename T> void ply_cast(void * dest, const char * src, bool be)
|
||||
{
|
||||
*(static_cast<T *>(dest)) = (be) ? endian_swap(*(reinterpret_cast<const T *>(src))) : *(reinterpret_cast<const T *>(src));
|
||||
}
|
||||
|
||||
template<typename T> void ply_cast_float(void * dest, const char * src, bool be)
|
||||
{
|
||||
*(static_cast<T *>(dest)) = (be) ? endian_swap_float(*(reinterpret_cast<const uint32_t *>(src))) : *(reinterpret_cast<const T *>(src));
|
||||
}
|
||||
|
||||
template<typename T> void ply_cast_double(void * dest, const char * src, bool be)
|
||||
{
|
||||
*(static_cast<T *>(dest)) = (be) ? endian_swap_double(*(reinterpret_cast<const uint64_t *>(src))) : *(reinterpret_cast<const T *>(src));
|
||||
}
|
||||
|
||||
template<typename T> T ply_read_ascii(std::istream & is)
|
||||
{
|
||||
T data;
|
||||
is >> data;
|
||||
return data;
|
||||
}
|
||||
|
||||
template<typename T> void ply_cast_ascii(void * dest, std::istream & is)
|
||||
{
|
||||
*(static_cast<T *>(dest)) = ply_read_ascii<T>(is);
|
||||
}
|
||||
|
||||
size_t find_element(const std::string & key, const std::vector<PlyElement> & list)
|
||||
{
|
||||
for (size_t i = 0; i < list.size(); i++) if (list[i].name == key) return i;
|
||||
return -1;
|
||||
}
|
||||
|
||||
size_t find_property(const std::string & key, const std::vector<PlyProperty> & list)
|
||||
{
|
||||
for (size_t i = 0; i < list.size(); ++i) if (list[i].name == key) return i;
|
||||
return -1;
|
||||
}
|
||||
|
||||
//////////////
|
||||
// PLY File //
|
||||
//////////////
|
||||
|
||||
bool PlyFile::PlyFileImpl::parse_header(std::istream & is)
|
||||
{
|
||||
std::string line;
|
||||
while (std::getline(is, line))
|
||||
{
|
||||
std::istringstream ls(line);
|
||||
std::string token;
|
||||
ls >> token;
|
||||
if (token == "ply" || token == "PLY" || token == "") continue;
|
||||
else if (token == "comment") read_header_text(line, ls, comments, 8);
|
||||
else if (token == "format") read_header_format(ls);
|
||||
else if (token == "element") read_header_element(ls);
|
||||
else if (token == "property") read_header_property(ls);
|
||||
else if (token == "obj_info") read_header_text(line, ls, objInfo, 9);
|
||||
else if (token == "end_header") break;
|
||||
else return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void PlyFile::PlyFileImpl::read_header_text(std::string line, std::istream & is, std::vector<std::string>& place, int erase)
|
||||
{
|
||||
place.push_back((erase > 0) ? line.erase(0, erase) : line);
|
||||
}
|
||||
|
||||
void PlyFile::PlyFileImpl::read_header_format(std::istream & is)
|
||||
{
|
||||
std::string s;
|
||||
(is >> s);
|
||||
if (s == "binary_little_endian") isBinary = true;
|
||||
else if (s == "binary_big_endian") isBinary = isBigEndian = true;
|
||||
}
|
||||
|
||||
void PlyFile::PlyFileImpl::read_header_element(std::istream & is)
|
||||
{
|
||||
elements.emplace_back(is);
|
||||
}
|
||||
|
||||
void PlyFile::PlyFileImpl::read_header_property(std::istream & is)
|
||||
{
|
||||
elements.back().properties.emplace_back(is);
|
||||
}
|
||||
|
||||
size_t PlyFile::PlyFileImpl::skip_property_binary(const PlyProperty & p, std::istream & is)
|
||||
{
|
||||
static std::vector<char> skip(PropertyTable[p.propertyType].stride);
|
||||
if (p.isList)
|
||||
{
|
||||
size_t listSize = 0;
|
||||
size_t dummyCount = 0;
|
||||
read_property_binary(p.listType, &listSize, dummyCount, is);
|
||||
for (size_t i = 0; i < listSize; ++i) is.read(skip.data(), PropertyTable[p.propertyType].stride);
|
||||
return listSize * PropertyTable[p.propertyType].stride; // in bytes
|
||||
}
|
||||
else
|
||||
{
|
||||
is.read(skip.data(), PropertyTable[p.propertyType].stride);
|
||||
return PropertyTable[p.propertyType].stride;
|
||||
}
|
||||
}
|
||||
|
||||
size_t PlyFile::PlyFileImpl::skip_property_ascii(const PlyProperty & p, std::istream & is)
|
||||
{
|
||||
std::string skip;
|
||||
if (p.isList)
|
||||
{
|
||||
size_t listSize = 0;
|
||||
size_t dummyCount = 0;
|
||||
read_property_ascii(p.listType, &listSize, dummyCount, is);
|
||||
for (size_t i = 0; i < listSize; ++i) is >> skip;
|
||||
return listSize * PropertyTable[p.propertyType].stride; // in bytes
|
||||
}
|
||||
else
|
||||
{
|
||||
is >> skip;
|
||||
return PropertyTable[p.propertyType].stride;
|
||||
}
|
||||
}
|
||||
|
||||
size_t PlyFile::PlyFileImpl::read_property_binary(const Type t, void * dest, size_t & destOffset, std::istream & is)
|
||||
{
|
||||
destOffset += PropertyTable[t].stride;
|
||||
|
||||
std::vector<char> src(PropertyTable[t].stride);
|
||||
is.read(src.data(), PropertyTable[t].stride);
|
||||
|
||||
switch (t)
|
||||
{
|
||||
case Type::INT8: ply_cast<int8_t>(dest, src.data(), isBigEndian); break;
|
||||
case Type::UINT8: ply_cast<uint8_t>(dest, src.data(), isBigEndian); break;
|
||||
case Type::INT16: ply_cast<int16_t>(dest, src.data(), isBigEndian); break;
|
||||
case Type::UINT16: ply_cast<uint16_t>(dest, src.data(), isBigEndian); break;
|
||||
case Type::INT32: ply_cast<int32_t>(dest, src.data(), isBigEndian); break;
|
||||
case Type::UINT32: ply_cast<uint32_t>(dest, src.data(), isBigEndian); break;
|
||||
case Type::FLOAT32: ply_cast_float<float>(dest, src.data(), isBigEndian); break;
|
||||
case Type::FLOAT64: ply_cast_double<double>(dest, src.data(), isBigEndian); break;
|
||||
case Type::INVALID: throw std::invalid_argument("invalid ply property");
|
||||
}
|
||||
|
||||
return PropertyTable[t].stride;
|
||||
}
|
||||
|
||||
size_t PlyFile::PlyFileImpl::read_property_ascii(const Type t, void * dest, size_t & destOffset, std::istream & is)
|
||||
{
|
||||
destOffset += PropertyTable[t].stride;
|
||||
|
||||
switch (t)
|
||||
{
|
||||
case Type::INT8: *((int8_t *)dest) = ply_read_ascii<int32_t>(is); break;
|
||||
case Type::UINT8: *((uint8_t *)dest) = ply_read_ascii<uint32_t>(is); break;
|
||||
case Type::INT16: ply_cast_ascii<int16_t>(dest, is); break;
|
||||
case Type::UINT16: ply_cast_ascii<uint16_t>(dest, is); break;
|
||||
case Type::INT32: ply_cast_ascii<int32_t>(dest, is); break;
|
||||
case Type::UINT32: ply_cast_ascii<uint32_t>(dest, is); break;
|
||||
case Type::FLOAT32: ply_cast_ascii<float>(dest, is); break;
|
||||
case Type::FLOAT64: ply_cast_ascii<double>(dest, is); break;
|
||||
case Type::INVALID: throw std::invalid_argument("invalid ply property");
|
||||
}
|
||||
return PropertyTable[t].stride;
|
||||
}
|
||||
|
||||
void PlyFile::PlyFileImpl::write_property_ascii(Type t, std::ostream & os, uint8_t * src, size_t & srcOffset)
|
||||
{
|
||||
switch (t)
|
||||
{
|
||||
case Type::INT8: os << static_cast<int32_t>(*reinterpret_cast<int8_t*>(src)); break;
|
||||
case Type::UINT8: os << static_cast<uint32_t>(*reinterpret_cast<uint8_t*>(src)); break;
|
||||
case Type::INT16: os << *reinterpret_cast<int16_t*>(src); break;
|
||||
case Type::UINT16: os << *reinterpret_cast<uint16_t*>(src); break;
|
||||
case Type::INT32: os << *reinterpret_cast<int32_t*>(src); break;
|
||||
case Type::UINT32: os << *reinterpret_cast<uint32_t*>(src); break;
|
||||
case Type::FLOAT32: os << *reinterpret_cast<float*>(src); break;
|
||||
case Type::FLOAT64: os << *reinterpret_cast<double*>(src); break;
|
||||
case Type::INVALID: throw std::invalid_argument("invalid ply property");
|
||||
}
|
||||
os << " ";
|
||||
srcOffset += PropertyTable[t].stride;
|
||||
}
|
||||
|
||||
void PlyFile::PlyFileImpl::write_property_binary(Type t, std::ostream & os, uint8_t * src, size_t & srcOffset)
|
||||
{
|
||||
os.write((char *)src, PropertyTable[t].stride);
|
||||
srcOffset += PropertyTable[t].stride;
|
||||
}
|
||||
|
||||
void PlyFile::PlyFileImpl::read(std::istream & is)
|
||||
{
|
||||
// Parse but only get the data size
|
||||
parse_data(is, true);
|
||||
|
||||
std::vector<std::shared_ptr<PlyData>> buffers;
|
||||
for (auto & entry : userData) buffers.push_back(entry.second.data);
|
||||
|
||||
// Since group-requested properties share the same cursor, we need to find unique cursors so we only allocate once
|
||||
std::sort(buffers.begin(), buffers.end());
|
||||
buffers.erase(std::unique(buffers.begin(), buffers.end()), buffers.end());
|
||||
|
||||
// Not great, but since we sorted by ptrs on PlyData, need to remap back onto its cursor in the userData table
|
||||
for (auto & b : buffers)
|
||||
{
|
||||
for (auto & entry : userData)
|
||||
{
|
||||
if (entry.second.data == b && b->buffer.get() == nullptr)
|
||||
{
|
||||
b->buffer = Buffer(entry.second.cursor->totalSizeBytes);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Populate the data
|
||||
parse_data(is, false);
|
||||
}
|
||||
|
||||
void PlyFile::PlyFileImpl::write(std::ostream & os, bool _isBinary)
|
||||
{
|
||||
if (_isBinary) write_binary_internal(os);
|
||||
else write_ascii_internal(os);
|
||||
}
|
||||
|
||||
void PlyFile::PlyFileImpl::write_binary_internal(std::ostream & os)
|
||||
{
|
||||
isBinary = true;
|
||||
write_header(os);
|
||||
|
||||
for (auto & e : elements)
|
||||
{
|
||||
for (size_t i = 0; i < e.size; ++i)
|
||||
{
|
||||
for (auto & p : e.properties)
|
||||
{
|
||||
auto & helper = userData[make_key(e.name, p.name)];
|
||||
if (p.isList)
|
||||
{
|
||||
uint8_t listSize[4] = {0, 0, 0, 0};
|
||||
std::memcpy(listSize, &p.listCount, sizeof(uint32_t));
|
||||
size_t dummyCount = 0;
|
||||
write_property_binary(p.listType, os, listSize, dummyCount);
|
||||
for (int j = 0; j < p.listCount; ++j)
|
||||
{
|
||||
write_property_binary(p.propertyType, os, (helper.data->buffer.get() + helper.cursor->byteOffset), helper.cursor->byteOffset);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
write_property_binary(p.propertyType, os, (helper.data->buffer.get() + helper.cursor->byteOffset), helper.cursor->byteOffset);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void PlyFile::PlyFileImpl::write_ascii_internal(std::ostream & os)
|
||||
{
|
||||
write_header(os);
|
||||
|
||||
for (auto & e : elements)
|
||||
{
|
||||
for (size_t i = 0; i < e.size; ++i)
|
||||
{
|
||||
for (auto & p : e.properties)
|
||||
{
|
||||
auto & helper = userData[make_key(e.name, p.name)];
|
||||
if (p.isList)
|
||||
{
|
||||
os << p.listCount << " ";
|
||||
for (int j = 0; j < p.listCount; ++j)
|
||||
{
|
||||
write_property_ascii(p.propertyType, os, (helper.data->buffer.get() + helper.cursor->byteOffset), helper.cursor->byteOffset);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
write_property_ascii(p.propertyType, os, (helper.data->buffer.get() + helper.cursor->byteOffset), helper.cursor->byteOffset);
|
||||
}
|
||||
}
|
||||
os << "\n";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void PlyFile::PlyFileImpl::write_header(std::ostream & os)
|
||||
{
|
||||
const std::locale & fixLoc = std::locale("C");
|
||||
os.imbue(fixLoc);
|
||||
|
||||
os << "ply\n";
|
||||
if (isBinary) os << ((isBigEndian) ? "format binary_big_endian 1.0" : "format binary_little_endian 1.0") << "\n";
|
||||
else os << "format ascii 1.0\n";
|
||||
|
||||
for (const auto & comment : comments) os << "comment " << comment << "\n";
|
||||
|
||||
for (auto & e : elements)
|
||||
{
|
||||
os << "element " << e.name << " " << e.size << "\n";
|
||||
for (const auto & p : e.properties)
|
||||
{
|
||||
if (p.isList)
|
||||
{
|
||||
os << "property list " << PropertyTable[p.listType].str << " "
|
||||
<< PropertyTable[p.propertyType].str << " " << p.name << "\n";
|
||||
}
|
||||
else
|
||||
{
|
||||
os << "property " << PropertyTable[p.propertyType].str << " " << p.name << "\n";
|
||||
}
|
||||
}
|
||||
}
|
||||
os << "end_header\n";
|
||||
}
|
||||
|
||||
// Returns the size (in bytes)
|
||||
std::shared_ptr<PlyData> PlyFile::PlyFileImpl::request_properties_from_element(const std::string & elementKey, const std::initializer_list<std::string> propertyKeys)
|
||||
{
|
||||
// All requested properties in the userDataTable share the same cursor (thrown into the same flat array)
|
||||
ParsingHelper helper;
|
||||
helper.data = std::make_shared<PlyData>();
|
||||
helper.data->count = 0;
|
||||
helper.data->t = Type::INVALID;
|
||||
helper.cursor = std::make_shared<PlyCursor>();
|
||||
helper.cursor->byteOffset = 0;
|
||||
helper.cursor->totalSizeBytes = 0;
|
||||
|
||||
if (elements.size() == 0) throw std::runtime_error("parsed header had no elements defined. malformed file?");
|
||||
if (!propertyKeys.size()) throw std::invalid_argument("`propertyKeys` argument is empty");
|
||||
if (elementKey.size() == 0) throw std::invalid_argument("`elementKey` argument is empty");
|
||||
|
||||
const int elementIndex = find_element(elementKey, elements);
|
||||
|
||||
// Sanity check if the user requested element is in the pre-parsed header
|
||||
if (elementIndex >= 0)
|
||||
{
|
||||
// We found the element
|
||||
const PlyElement & element = elements[elementIndex];
|
||||
|
||||
helper.data->count = element.size;
|
||||
|
||||
// Find each of the keys
|
||||
for (auto key : propertyKeys)
|
||||
{
|
||||
const int propertyIndex = find_property(key, element.properties);
|
||||
|
||||
if (propertyIndex >= 0)
|
||||
{
|
||||
// We found the property
|
||||
const PlyProperty & property = element.properties[propertyIndex];
|
||||
|
||||
helper.data->t = property.propertyType; // hmm....
|
||||
|
||||
auto result = userData.insert(std::pair<std::string, ParsingHelper>(make_key(element.name, property.name), helper));
|
||||
if (result.second == false) throw std::invalid_argument("element-property key has already been requested: " + make_key(element.name, property.name));
|
||||
}
|
||||
else throw std::invalid_argument("one of the property keys was not found in the header: " + key);
|
||||
}
|
||||
}
|
||||
else throw std::invalid_argument("the element key was not found in the header: " + elementKey);
|
||||
|
||||
return helper.data;
|
||||
}
|
||||
|
||||
void PlyFile::PlyFileImpl::add_properties_to_element(const std::string & elementKey, const std::initializer_list<std::string> propertyKeys, const Type type, const size_t count, uint8_t * data, const Type listType, const size_t listCount)
|
||||
{
|
||||
ParsingHelper helper;
|
||||
helper.data = std::make_shared<PlyData>();
|
||||
helper.data->count = count;
|
||||
helper.data->t = type;
|
||||
helper.data->buffer = Buffer(data);
|
||||
helper.cursor = std::make_shared<PlyCursor>();
|
||||
helper.cursor->byteOffset = 0;
|
||||
helper.cursor->totalSizeBytes = 0;
|
||||
|
||||
auto create_property_on_element = [&](PlyElement & e)
|
||||
{
|
||||
for (auto key : propertyKeys)
|
||||
{
|
||||
PlyProperty newProp = (listType == Type::INVALID) ? PlyProperty(type, key) : PlyProperty(listType, type, key, listCount);
|
||||
/* auto result = */userData.insert(std::pair<std::string, ParsingHelper>(make_key(elementKey, key), helper));
|
||||
e.properties.push_back(newProp);
|
||||
}
|
||||
};
|
||||
|
||||
int idx = find_element(elementKey, elements);
|
||||
if (idx >= 0)
|
||||
{
|
||||
PlyElement & e = elements[idx];
|
||||
create_property_on_element(e);
|
||||
}
|
||||
else
|
||||
{
|
||||
PlyElement newElement = (listType == Type::INVALID) ? PlyElement(elementKey, count / propertyKeys.size()) : PlyElement(elementKey, count / listCount);
|
||||
create_property_on_element(newElement);
|
||||
elements.push_back(newElement);
|
||||
}
|
||||
}
|
||||
|
||||
void PlyFile::PlyFileImpl::parse_data(std::istream & is, bool firstPass)
|
||||
{
|
||||
std::function<size_t(const Type t, void * dest, size_t & destOffset, std::istream & is)> read;
|
||||
std::function<size_t(const PlyProperty & p, std::istream & is)> skip;
|
||||
|
||||
const auto start = is.tellg();
|
||||
|
||||
if (isBinary)
|
||||
{
|
||||
read = [&](const Type t, void * dest, size_t & destOffset, std::istream & _is) { return read_property_binary(t, dest, destOffset, _is); };
|
||||
skip = [&](const PlyProperty & p, std::istream & _is) { return skip_property_binary(p, _is); };
|
||||
}
|
||||
else
|
||||
{
|
||||
read = [&](const Type t, void * dest, size_t & destOffset, std::istream & _is) { return read_property_ascii(t, dest, destOffset, _is); };
|
||||
skip = [&](const PlyProperty & p, std::istream & _is) { return skip_property_ascii(p, _is); };
|
||||
}
|
||||
|
||||
for (auto & element : elements)
|
||||
{
|
||||
for (size_t count = 0; count < element.size; ++count)
|
||||
{
|
||||
for (auto & property : element.properties)
|
||||
{
|
||||
auto cursorIt = userData.find(make_key(element.name, property.name));
|
||||
if (cursorIt != userData.end())
|
||||
{
|
||||
auto & helper = cursorIt->second;
|
||||
if (!firstPass)
|
||||
{
|
||||
if (property.isList)
|
||||
{
|
||||
size_t listSize = 0;
|
||||
size_t dummyCount = 0;
|
||||
read(property.listType, &listSize, dummyCount, is);
|
||||
for (size_t i = 0; i < listSize; ++i)
|
||||
{
|
||||
read(property.propertyType, (helper.data->buffer.get() + helper.cursor->byteOffset), helper.cursor->byteOffset, is);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
read(property.propertyType, (helper.data->buffer.get() + helper.cursor->byteOffset), helper.cursor->byteOffset, is);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
helper.cursor->totalSizeBytes += skip(property, is);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
skip(property, is);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Reset istream reader to the beginning
|
||||
if (firstPass) is.seekg(start, is.beg);
|
||||
}
|
||||
|
||||
///////////////////////////////////
|
||||
// Pass-Through Public Interface //
|
||||
///////////////////////////////////
|
||||
|
||||
PlyFile::PlyFile() { impl.reset(new PlyFileImpl()); };
|
||||
PlyFile::~PlyFile() { };
|
||||
bool PlyFile::parse_header(std::istream & is) { return impl->parse_header(is); }
|
||||
void PlyFile::read(std::istream & is) { return impl->read(is); }
|
||||
void PlyFile::write(std::ostream & os, bool isBinary) { return impl->write(os, isBinary); }
|
||||
std::vector<PlyElement> PlyFile::get_elements() const { return impl->elements; }
|
||||
std::vector<std::string> & PlyFile::get_comments() { return impl->comments; }
|
||||
std::vector<std::string> PlyFile::get_info() const { return impl->objInfo; }
|
||||
std::shared_ptr<PlyData> PlyFile::request_properties_from_element(const std::string & elementKey, const std::initializer_list<std::string> propertyKeys)
|
||||
{
|
||||
return impl->request_properties_from_element(elementKey, propertyKeys);
|
||||
}
|
||||
void PlyFile::add_properties_to_element(const std::string & elementKey, const std::initializer_list<std::string> propertyKeys, const Type type, const size_t count, uint8_t * data, const Type listType, const size_t listCount)
|
||||
{
|
||||
return impl->add_properties_to_element(elementKey, propertyKeys, type, count, data, listType, listCount);
|
||||
}
|
|
@ -1,119 +0,0 @@
|
|||
// This software is in the public domain. Where that dedication is not
|
||||
// recognized, you are granted a perpetual, irrevocable license to copy,
|
||||
// distribute, and modify this file as you see fit.
|
||||
// Authored in 2015 by Dimitri Diakopoulos (http://www.dimitridiakopoulos.com)
|
||||
// https://github.com/ddiakopoulos/tinyply
|
||||
// Version 2.0
|
||||
|
||||
#ifndef tinyply_h
|
||||
#define tinyply_h
|
||||
|
||||
#include <vector>
|
||||
#include <string>
|
||||
#include <stdint.h>
|
||||
#include <sstream>
|
||||
#include <memory>
|
||||
#include <map>
|
||||
|
||||
namespace tinyply
|
||||
{
|
||||
|
||||
enum class Type : uint8_t
|
||||
{
|
||||
INVALID,
|
||||
INT8,
|
||||
UINT8,
|
||||
INT16,
|
||||
UINT16,
|
||||
INT32,
|
||||
UINT32,
|
||||
FLOAT32,
|
||||
FLOAT64
|
||||
};
|
||||
|
||||
struct PropertyInfo
|
||||
{
|
||||
int stride;
|
||||
std::string str;
|
||||
};
|
||||
|
||||
static std::map<Type, PropertyInfo> PropertyTable
|
||||
{
|
||||
{ Type::INT8,{ 1, "char" } },
|
||||
{ Type::UINT8,{ 1, "uchar" } },
|
||||
{ Type::INT16,{ 2, "short" } },
|
||||
{ Type::UINT16,{ 2, "ushort" } },
|
||||
{ Type::INT32,{ 4, "int" } },
|
||||
{ Type::UINT32,{ 4, "uint" } },
|
||||
{ Type::FLOAT32,{ 4, "float" } },
|
||||
{ Type::FLOAT64,{ 8, "double" } },
|
||||
{ Type::INVALID,{ 0, "INVALID" } }
|
||||
};
|
||||
|
||||
class Buffer
|
||||
{
|
||||
uint8_t * alias{ nullptr };
|
||||
struct delete_array { void operator()(uint8_t * p) { delete[] p; } };
|
||||
std::unique_ptr<uint8_t, decltype(Buffer::delete_array())> data;
|
||||
size_t size;
|
||||
public:
|
||||
Buffer() {};
|
||||
Buffer(const size_t size) : data(new uint8_t[size], delete_array()), size(size) { alias = data.get(); } // allocating
|
||||
Buffer(uint8_t * ptr) { alias = ptr; } // non-allocating, fixme: set size?
|
||||
uint8_t * get() { return alias; }
|
||||
size_t size_bytes() const { return size; }
|
||||
};
|
||||
|
||||
struct PlyData
|
||||
{
|
||||
Type t;
|
||||
size_t count;
|
||||
Buffer buffer;
|
||||
};
|
||||
|
||||
struct PlyProperty
|
||||
{
|
||||
PlyProperty(std::istream & is);
|
||||
PlyProperty(Type type, std::string & _name) : name(_name), propertyType(type) {}
|
||||
PlyProperty(Type list_type, Type prop_type, std::string & _name, int list_count) : name(_name), propertyType(prop_type), isList(true), listType(list_type), listCount(list_count) {}
|
||||
std::string name;
|
||||
Type propertyType;
|
||||
bool isList{ false };
|
||||
Type listType{ Type::INVALID };
|
||||
int listCount{ 0 };
|
||||
};
|
||||
|
||||
struct PlyElement
|
||||
{
|
||||
PlyElement(std::istream & istream);
|
||||
PlyElement(const std::string & _name, size_t count) : name(_name), size(count) {}
|
||||
std::string name;
|
||||
size_t size;
|
||||
std::vector<PlyProperty> properties;
|
||||
};
|
||||
|
||||
struct PlyFile
|
||||
{
|
||||
struct PlyFileImpl;
|
||||
std::unique_ptr<PlyFileImpl> impl;
|
||||
|
||||
PlyFile();
|
||||
~PlyFile();
|
||||
|
||||
bool parse_header(std::istream & is);
|
||||
|
||||
void read(std::istream & is);
|
||||
|
||||
void write(std::ostream & os, bool isBinary);
|
||||
|
||||
std::vector<PlyElement> get_elements() const;
|
||||
std::vector<std::string> & get_comments();
|
||||
std::vector<std::string> get_info() const;
|
||||
|
||||
std::shared_ptr<PlyData> request_properties_from_element(const std::string & elementKey, const std::initializer_list<std::string> propertyKeys);
|
||||
void add_properties_to_element(const std::string & elementKey, const std::initializer_list<std::string> propertyKeys, const Type type, const size_t count, uint8_t * data, const Type listType, const size_t listCount);
|
||||
};
|
||||
|
||||
} // namesapce tinyply
|
||||
|
||||
#endif // tinyply_h
|
|
@ -1,285 +0,0 @@
|
|||
#include <vector>
|
||||
#include <map>
|
||||
#include <stdio.h>
|
||||
#include <glm/glm.hpp>
|
||||
#include <iostream>
|
||||
#include "vboindexer.hpp"
|
||||
#include <string.h> // for memcmp
|
||||
|
||||
|
||||
// Returns true iif v1 can be considered equal to v2
|
||||
bool is_near(float v1, float v2){
|
||||
return fabs( v1-v2 ) < 0.01f;
|
||||
}
|
||||
|
||||
// Searches through all already-exported vertices
|
||||
// for a similar one.
|
||||
// Similar = same position + same UVs + same normal
|
||||
bool getSimilarVertexIndex(
|
||||
glm::vec3 & in_vertex,
|
||||
glm::vec2 & in_uv,
|
||||
glm::vec3 & in_normal,
|
||||
std::vector<glm::vec3> & out_vertices,
|
||||
std::vector<glm::vec2> & out_uvs,
|
||||
std::vector<glm::vec3> & out_normals,
|
||||
unsigned int & result
|
||||
){
|
||||
// Lame linear search
|
||||
for ( unsigned int i=0; i<out_vertices.size(); i++ ){
|
||||
if (
|
||||
is_near( in_vertex.x , out_vertices[i].x ) &&
|
||||
is_near( in_vertex.y , out_vertices[i].y ) &&
|
||||
is_near( in_vertex.z , out_vertices[i].z ) &&
|
||||
is_near( in_uv.x , out_uvs [i].x ) &&
|
||||
is_near( in_uv.y , out_uvs [i].y ) &&
|
||||
is_near( in_normal.x , out_normals [i].x ) &&
|
||||
is_near( in_normal.y , out_normals [i].y ) &&
|
||||
is_near( in_normal.z , out_normals [i].z )
|
||||
){
|
||||
result = i;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
// No other vertex could be used instead.
|
||||
// Looks like we'll have to add it to the VBO.
|
||||
return false;
|
||||
}
|
||||
|
||||
void indexVBO_slow(
|
||||
std::vector<glm::vec3> & in_vertices,
|
||||
std::vector<glm::vec2> & in_uvs,
|
||||
std::vector<glm::vec3> & in_normals,
|
||||
|
||||
std::vector<unsigned int> & out_indices,
|
||||
std::vector<glm::vec3> & out_vertices,
|
||||
std::vector<glm::vec2> & out_uvs,
|
||||
std::vector<glm::vec3> & out_normals
|
||||
){
|
||||
// For each input vertex
|
||||
for ( unsigned int i=0; i<in_vertices.size(); i++ ){
|
||||
|
||||
// Try to find a similar vertex in out_XXXX
|
||||
unsigned int index;
|
||||
bool found = getSimilarVertexIndex(in_vertices[i], in_uvs[i], in_normals[i], out_vertices, out_uvs, out_normals, index);
|
||||
|
||||
if ( found ){ // A similar vertex is already in the VBO, use it instead !
|
||||
out_indices .push_back( index );
|
||||
}else{ // If not, it needs to be added in the output data.
|
||||
out_vertices.push_back( in_vertices[i]);
|
||||
out_uvs .push_back( in_uvs[i]);
|
||||
out_normals .push_back( in_normals[i]);
|
||||
out_indices .push_back( (unsigned int)out_vertices.size() - 1 );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
struct PackedVertex{
|
||||
glm::vec3 position;
|
||||
glm::vec2 uv;
|
||||
glm::vec3 normal;
|
||||
bool operator<(const PackedVertex that) const{
|
||||
return memcmp((void*)this, (void*)&that, sizeof(PackedVertex))>0;
|
||||
};
|
||||
};
|
||||
|
||||
bool getSimilarVertexIndex_fast(
|
||||
PackedVertex & packed,
|
||||
std::map<PackedVertex,unsigned int> & VertexToOutIndex,
|
||||
unsigned int & result
|
||||
){
|
||||
std::map<PackedVertex,unsigned int>::iterator it = VertexToOutIndex.find(packed);
|
||||
if ( it == VertexToOutIndex.end() ){
|
||||
return false;
|
||||
}else{
|
||||
result = it->second;
|
||||
// printf("it->second %lu\n", it->second);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
void indexVBO(
|
||||
std::vector<glm::vec3> & in_vertices,
|
||||
std::vector<glm::vec2> & in_uvs,
|
||||
std::vector<glm::vec3> & in_normals,
|
||||
|
||||
std::vector<unsigned int> & out_indices,
|
||||
std::vector<glm::vec3> & out_vertices,
|
||||
std::vector<glm::vec2> & out_uvs,
|
||||
std::vector<glm::vec3> & out_normals
|
||||
){
|
||||
std::map<PackedVertex,unsigned int> VertexToOutIndex;
|
||||
|
||||
// For each input vertex
|
||||
for ( unsigned int i=0; i<in_vertices.size(); i++ ){
|
||||
|
||||
PackedVertex packed = {in_vertices[i], in_uvs[i], in_normals[i]};
|
||||
|
||||
// Try to find a similar vertex in out_XXXX
|
||||
unsigned int index;
|
||||
bool found = getSimilarVertexIndex_fast( packed, VertexToOutIndex, index);
|
||||
|
||||
if ( found ){ // A similar vertex is already in the VBO, use it instead !
|
||||
out_indices .push_back( index );
|
||||
// printf("found bef %lu %lu\n", i, index);
|
||||
}else{ // If not, it needs to be added in the output data.
|
||||
out_vertices.push_back( in_vertices[i]);
|
||||
out_uvs .push_back( in_uvs[i]);
|
||||
out_normals .push_back( in_normals[i]);
|
||||
unsigned int newindex = (unsigned int)out_vertices.size() - 1;
|
||||
out_indices .push_back( newindex );
|
||||
VertexToOutIndex[ packed ] = newindex;
|
||||
}
|
||||
}
|
||||
// printf("Size of output vertex vector %lu\n", out_vertices.size());
|
||||
}
|
||||
|
||||
// TODO: Inplement index_SEM from load MTL
|
||||
void indexVBO_MTL(
|
||||
std::vector<std::vector<glm::vec3>> & mtl_vertices,
|
||||
std::vector<std::vector<glm::vec2>> & mtl_uvs,
|
||||
std::vector<std::vector<glm::vec3>> & mtl_normals,
|
||||
|
||||
std::vector<unsigned int> & out_indices,
|
||||
std::vector<glm::vec3> & out_vertices,
|
||||
std::vector<glm::vec2> & out_uvs,
|
||||
std::vector<glm::vec3> & out_normals,
|
||||
std::vector<glm::vec2> & out_semantics
|
||||
) {
|
||||
std::map<PackedVertex,unsigned int> VertexToOutIndex;
|
||||
|
||||
// In group j
|
||||
bool use_uvs = mtl_uvs.size() > 0;
|
||||
bool use_normals = mtl_normals.size() > 0;
|
||||
if (!((use_uvs && mtl_vertices.size() == mtl_vertices.size()) ||
|
||||
(use_normals && mtl_normals.size() == mtl_normals.size()))) {
|
||||
printf("VBO Indexer error: size missmatch. Vertex (%lu) uvs (%lu) normals (%lu)\n", mtl_vertices.size(), mtl_uvs.size(), mtl_normals.size());
|
||||
}
|
||||
std::vector<glm::vec3> group_vertices;
|
||||
std::vector<glm::vec2> group_uvs;
|
||||
std::vector<glm::vec3> group_normals;
|
||||
|
||||
printf("Indexing VBO total groups: %lu\n", mtl_vertices.size());
|
||||
for (int j=0; j<mtl_vertices.size(); j++ ) {
|
||||
group_vertices = mtl_vertices[j];
|
||||
if (use_uvs) group_uvs = mtl_uvs[j];
|
||||
if (use_normals) group_normals = mtl_normals[j];
|
||||
|
||||
//printf("Group (%d/%d) size vertex %d\n", j, mtl_vertices.size(), group_vertices.size());
|
||||
for (int i=0; i<group_vertices.size(); i++ ) {
|
||||
//printf("\t subgroup size %d/%d %d/%d\n", j, mtl_vertices.size(), i, group_vertices.size());
|
||||
|
||||
PackedVertex packed = {group_vertices[i], glm::vec2(), glm::vec3()};
|
||||
unsigned int index;
|
||||
bool found = getSimilarVertexIndex_fast( packed, VertexToOutIndex, index);
|
||||
glm::vec2 semantic_uv;
|
||||
semantic_uv.x = (float)j;
|
||||
semantic_uv.y = 0;
|
||||
|
||||
found = false;
|
||||
if ( found ) {
|
||||
out_indices.push_back( index );
|
||||
} else {
|
||||
// Disable vertex indexing
|
||||
out_vertices.push_back( group_vertices[i]);
|
||||
out_semantics.push_back( semantic_uv);
|
||||
unsigned int newindex = (unsigned int)out_vertices.size() - 1;
|
||||
out_indices.push_back( newindex);
|
||||
if (use_uvs) out_uvs.push_back( group_uvs[i]);
|
||||
if (use_normals) out_normals.push_back( group_normals[i]);
|
||||
VertexToOutIndex [ packed ] = newindex;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// TODO: Inplement index_SEM from load MTL
|
||||
void indexVBO_PLY(
|
||||
std::vector<std::vector<glm::vec3>> & mtl_vertices,
|
||||
std::vector<std::vector<glm::vec2>> & mtl_uvs,
|
||||
std::vector<std::vector<glm::vec3>> & mtl_normals,
|
||||
|
||||
std::vector<unsigned int> & out_indices,
|
||||
std::vector<glm::vec3> & out_vertices,
|
||||
std::vector<glm::vec2> & out_uvs,
|
||||
std::vector<glm::vec3> & out_normals,
|
||||
std::vector<glm::vec2> & out_semantics
|
||||
) {
|
||||
std::map<PackedVertex,unsigned int> VertexToOutIndex;
|
||||
|
||||
// In group j
|
||||
for (int j=0; j<mtl_vertices.size(); j++ ) {
|
||||
std::vector<glm::vec3> group_vertices = mtl_vertices[j];
|
||||
std::vector<glm::vec2> group_uvs = mtl_uvs[j];
|
||||
std::vector<glm::vec3> group_normals = mtl_normals[j];
|
||||
//float semantic_layer = (float) 0;
|
||||
//float semantic_layer = (float) j;
|
||||
|
||||
uint group_size = group_vertices.size();
|
||||
if (group_uvs.size() < group_size)
|
||||
group_size = group_uvs.size();
|
||||
|
||||
for (int i=0; i<group_size; i++ ) {
|
||||
PackedVertex packed = {group_vertices[i], group_uvs[i], group_normals[i]};
|
||||
unsigned int index;
|
||||
bool found = getSimilarVertexIndex_fast( packed, VertexToOutIndex, index);
|
||||
glm::vec2 semantic_uv;
|
||||
semantic_uv.x = (float)j;//semantic_layer;
|
||||
semantic_uv.y = 0;
|
||||
|
||||
// Disable vertex indexing
|
||||
found = false;
|
||||
if ( found ) {
|
||||
out_indices.push_back( index );
|
||||
} else {
|
||||
out_vertices .push_back( group_vertices[i]);
|
||||
out_uvs .push_back( group_uvs[i]);
|
||||
out_normals .push_back( group_normals[i]);
|
||||
out_semantics.push_back( semantic_uv);
|
||||
unsigned int newindex = (unsigned int)out_vertices.size() - 1;
|
||||
out_indices .push_back( newindex);
|
||||
|
||||
VertexToOutIndex [ packed ] = newindex;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void indexVBO_TBN(
|
||||
std::vector<glm::vec3> & in_vertices,
|
||||
std::vector<glm::vec2> & in_uvs,
|
||||
std::vector<glm::vec3> & in_normals,
|
||||
std::vector<glm::vec3> & in_tangents,
|
||||
std::vector<glm::vec3> & in_bitangents,
|
||||
|
||||
std::vector<unsigned int> & out_indices,
|
||||
std::vector<glm::vec3> & out_vertices,
|
||||
std::vector<glm::vec2> & out_uvs,
|
||||
std::vector<glm::vec3> & out_normals,
|
||||
std::vector<glm::vec3> & out_tangents,
|
||||
std::vector<glm::vec3> & out_bitangents
|
||||
){
|
||||
// For each input vertex
|
||||
for ( unsigned int i=0; i<in_vertices.size(); i++ ){
|
||||
|
||||
// Try to find a similar vertex in out_XXXX
|
||||
unsigned int index;
|
||||
bool found = getSimilarVertexIndex(in_vertices[i], in_uvs[i], in_normals[i], out_vertices, out_uvs, out_normals, index);
|
||||
|
||||
if ( found ){ // A similar vertex is already in the VBO, use it instead !
|
||||
out_indices.push_back( index );
|
||||
|
||||
// Average the tangents and the bitangents
|
||||
out_tangents[index] += in_tangents[i];
|
||||
out_bitangents[index] += in_bitangents[i];
|
||||
}else{ // If not, it needs to be added in the output data.
|
||||
out_vertices.push_back( in_vertices[i]);
|
||||
out_uvs .push_back( in_uvs[i]);
|
||||
out_normals .push_back( in_normals[i]);
|
||||
out_tangents .push_back( in_tangents[i]);
|
||||
out_bitangents .push_back( in_bitangents[i]);
|
||||
out_indices .push_back( (unsigned int)out_vertices.size() - 1 );
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,54 +0,0 @@
|
|||
#ifndef VBOINDEXER_HPP
|
||||
#define VBOINDEXER_HPP
|
||||
|
||||
void indexVBO(
|
||||
std::vector<glm::vec3> & in_vertices,
|
||||
std::vector<glm::vec2> & in_uvs,
|
||||
std::vector<glm::vec3> & in_normals,
|
||||
|
||||
std::vector<unsigned int> & out_indices,
|
||||
std::vector<glm::vec3> & out_vertices,
|
||||
std::vector<glm::vec2> & out_uvs,
|
||||
std::vector<glm::vec3> & out_normals
|
||||
);
|
||||
|
||||
void indexVBO_MTL(
|
||||
std::vector<std::vector<glm::vec3>> & mtl_vertices,
|
||||
std::vector<std::vector<glm::vec2>> & mtl_uvs,
|
||||
std::vector<std::vector<glm::vec3>> & mtl_normals,
|
||||
|
||||
std::vector<unsigned int> & out_indices,
|
||||
std::vector<glm::vec3> & out_vertices,
|
||||
std::vector<glm::vec2> & out_uvs,
|
||||
std::vector<glm::vec3> & out_normals,
|
||||
std::vector<glm::vec2> & out_semantics
|
||||
);
|
||||
|
||||
void indexVBO_PLY(
|
||||
std::vector<std::vector<glm::vec3>> & mtl_vertices,
|
||||
std::vector<std::vector<glm::vec2>> & mtl_uvs,
|
||||
std::vector<std::vector<glm::vec3>> & mtl_normals,
|
||||
|
||||
std::vector<unsigned int> & out_indices,
|
||||
std::vector<glm::vec3> & out_vertices,
|
||||
std::vector<glm::vec2> & out_uvs,
|
||||
std::vector<glm::vec3> & out_normals,
|
||||
std::vector<glm::vec2> & out_semantics
|
||||
);
|
||||
|
||||
void indexVBO_TBN(
|
||||
std::vector<glm::vec3> & in_vertices,
|
||||
std::vector<glm::vec2> & in_uvs,
|
||||
std::vector<glm::vec3> & in_normals,
|
||||
std::vector<glm::vec3> & in_tangents,
|
||||
std::vector<glm::vec3> & in_bitangents,
|
||||
|
||||
std::vector<unsigned int> & out_indices,
|
||||
std::vector<glm::vec3> & out_vertices,
|
||||
std::vector<glm::vec2> & out_uvs,
|
||||
std::vector<glm::vec3> & out_normals,
|
||||
std::vector<glm::vec3> & out_tangents,
|
||||
std::vector<glm::vec3> & out_bitangents
|
||||
);
|
||||
|
||||
#endif
|
|
@ -1,11 +0,0 @@
|
|||
## Usage: random_husky.py debugging
|
||||
import os
|
||||
from gibson.data.datasets import get_model_path
|
||||
|
||||
|
||||
def run_depth_render():
|
||||
model_path = get_model_path()[0]
|
||||
dr_path = os.path.join(os.path.dirname(os.path.abspath(__file__)), 'depth_render')
|
||||
os.chdir(dr_path)
|
||||
print("./depth_render --modelpath {}".format(model_path))
|
||||
os.system("./depth_render --modelpath {}".format(model_path))
|
|
@ -1,106 +0,0 @@
|
|||
#version 330 core
|
||||
|
||||
// Interpolated values from the vertex shaders
|
||||
in vec2 UV;
|
||||
in vec3 Position_worldspace;
|
||||
in vec3 Normal_cameraspace;
|
||||
in vec3 EyeDirection_cameraspace;
|
||||
in vec3 LightDirection_cameraspace;
|
||||
|
||||
// Ouput data
|
||||
//layout(location = 0) out vec3 color;
|
||||
layout(location = 0) out vec3 mist;
|
||||
|
||||
// Values that stay constant for the whole mesh.
|
||||
uniform sampler2D myTextureSampler;
|
||||
uniform mat4 MV;
|
||||
uniform vec3 LightPosition_worldspace;
|
||||
|
||||
void main(){
|
||||
|
||||
// Light emission properties
|
||||
// You probably want to put them as uniforms
|
||||
vec3 LightColor = vec3(1,1,1);
|
||||
float LightPower = 50.0f;
|
||||
|
||||
// Material properties
|
||||
vec3 MaterialDiffuseColor = texture( myTextureSampler, UV ).rgb;
|
||||
vec3 MaterialAmbientColor = vec3(0.1,0.1,0.1) * MaterialDiffuseColor;
|
||||
vec3 MaterialSpecularColor = vec3(0.3,0.3,0.3);
|
||||
|
||||
// Distance to the light
|
||||
float distance = length( LightPosition_worldspace - Position_worldspace );
|
||||
|
||||
// Normal of the computed fragment, in camera space
|
||||
vec3 n = normalize( Normal_cameraspace );
|
||||
// Direction of the light (from the fragment to the light)
|
||||
vec3 l = normalize( LightDirection_cameraspace );
|
||||
// Cosine of the angle between the normal and the light direction,
|
||||
// clamped above 0
|
||||
// - light is at the vertical of the triangle -> 1
|
||||
// - light is perpendiular to the triangle -> 0
|
||||
// - light is behind the triangle -> 0
|
||||
float cosTheta = clamp( dot( n,l ), 0,1 );
|
||||
|
||||
// Eye vector (towards the camera)
|
||||
vec3 E = normalize(EyeDirection_cameraspace);
|
||||
// Direction in which the triangle reflects the light
|
||||
vec3 R = reflect(-l,n);
|
||||
// Cosine of the angle between the Eye vector and the Reflect vector,
|
||||
// clamped to 0
|
||||
// - Looking into the reflection -> 1
|
||||
// - Looking elsewhere -> < 1
|
||||
float cosAlpha = clamp( dot( E,R ), 0,1 );
|
||||
|
||||
/*color =
|
||||
// Ambient : simulates indirect lighting
|
||||
MaterialAmbientColor +
|
||||
// Diffuse : "color" of the object
|
||||
MaterialDiffuseColor * LightColor * LightPower * cosTheta / (distance*distance) +
|
||||
// Specular : reflective highlight, like a mirror
|
||||
MaterialSpecularColor * LightColor * LightPower * pow(cosAlpha,5) / (distance*distance);
|
||||
*/
|
||||
|
||||
const vec3 bitShift3 = vec3(65536.0, 256.0, 1.0);
|
||||
const vec3 bitMask3 = vec3(0.0, 1.0/256.0, 1.0/256.0);
|
||||
//float A = gl_ProjectionMatrix[2].z;
|
||||
//float B = gl_ProjectionMatrix[3].z;
|
||||
float zNear = 0.1f; //- B / (1.0 - A);
|
||||
float zFar = 5000f;// B / (1.0 + A);
|
||||
float depthN = abs(EyeDirection_cameraspace.z - zNear)/128; // scale to a value in [0, 1]
|
||||
vec3 depthNPack3 = fract(depthN*bitShift3);
|
||||
depthNPack3 -= depthNPack3.xxy*bitMask3;
|
||||
|
||||
//depth = depthNPack3;
|
||||
|
||||
//depth = vec3(EyeDirection_cameraspace.z/128, EyeDirection_cameraspace.z/128, EyeDirection_cameraspace.z/128);
|
||||
|
||||
//float m = sqrt(EyeDirection_cameraspace.x * EyeDirection_cameraspace.x + EyeDirection_cameraspace.y * EyeDirection_cameraspace.y + EyeDirection_cameraspace.z * EyeDirection_cameraspace.z);
|
||||
float m = length(EyeDirection_cameraspace.y);
|
||||
// float cosine = sqrt(EyeDirection_cameraspace.x * EyeDirection_cameraspace.x + EyeDirection_cameraspace.y * EyeDirection_cameraspace.y) / sqrt(EyeDirection_cameraspace.x * EyeDirection_cameraspace.x + EyeDirection_cameraspace.y * EyeDirection_cameraspace.y + EyeDirection_cameraspace.z * EyeDirection_cameraspace.z);
|
||||
//float cosine = 1;
|
||||
|
||||
//if (dot(E, n) >= -0.05f ) {
|
||||
// m = 0.0f;
|
||||
//} else {
|
||||
// m = 128.0f;
|
||||
//}
|
||||
|
||||
//comment this out to disable mist
|
||||
mist = vec3(m, m, m);
|
||||
|
||||
float cull_delta = 0.7f;
|
||||
|
||||
|
||||
|
||||
//if (dot(EyeDirection_cameraspace, Normal_cameraspace) >= 0) {
|
||||
// mist = mist - cull_delta;
|
||||
//}
|
||||
|
||||
//mist = vec3(cosine, cosine, cosine);
|
||||
|
||||
//depth = vec3(depthN * 65536, depthN * 65536, depthN * 65536);
|
||||
|
||||
//depth = (EyeDirection_cameraspace.z <=0)? vec3(0, 0, 0): vec3(1, 1, 1);
|
||||
//depth = vec3(0.5, 0.5, 0.5);
|
||||
}
|
|
@ -1,85 +0,0 @@
|
|||
#version 330 core
|
||||
|
||||
// Interpolated values from the vertex shaders
|
||||
in vec2 UV;
|
||||
in vec3 Position_worldspace;
|
||||
in vec3 Normal_cameraspace;
|
||||
in vec3 EyeDirection_cameraspace;
|
||||
in vec3 LightDirection_cameraspace;
|
||||
|
||||
// Ouput data
|
||||
//layout(location = 0) out vec3 color;
|
||||
layout(location = 0) out vec3 mist;
|
||||
|
||||
// Values that stay constant for the whole mesh.
|
||||
uniform sampler2D myTextureSampler;
|
||||
uniform mat4 MV;
|
||||
uniform vec3 LightPosition_worldspace;
|
||||
|
||||
void main(){
|
||||
|
||||
// Light emission properties
|
||||
// You probably want to put them as uniforms
|
||||
vec3 LightColor = vec3(1,1,1);
|
||||
float LightPower = 50.0f;
|
||||
|
||||
// Material properties
|
||||
vec3 MaterialDiffuseColor = texture( myTextureSampler, UV ).rgb;
|
||||
vec3 MaterialAmbientColor = vec3(0.1,0.1,0.1) * MaterialDiffuseColor;
|
||||
vec3 MaterialSpecularColor = vec3(0.3,0.3,0.3);
|
||||
|
||||
// Distance to the light
|
||||
float distance = length( LightPosition_worldspace - Position_worldspace );
|
||||
|
||||
// Normal of the computed fragment, in camera space
|
||||
vec3 n = normalize( Normal_cameraspace );
|
||||
// Direction of the light (from the fragment to the light)
|
||||
vec3 l = normalize( LightDirection_cameraspace );
|
||||
// Cosine of the angle between the normal and the light direction,
|
||||
// clamped above 0
|
||||
// - light is at the vertical of the triangle -> 1
|
||||
// - light is perpendiular to the triangle -> 0
|
||||
// - light is behind the triangle -> 0
|
||||
float cosTheta = clamp( dot( n,l ), 0,1 );
|
||||
|
||||
// Eye vector (towards the camera)
|
||||
vec3 E = normalize(EyeDirection_cameraspace);
|
||||
// Direction in which the triangle reflects the light
|
||||
vec3 R = reflect(-l,n);
|
||||
// Cosine of the angle between the Eye vector and the Reflect vector,
|
||||
// clamped to 0
|
||||
// - Looking into the reflection -> 1
|
||||
// - Looking elsewhere -> < 1
|
||||
float cosAlpha = clamp( dot( E,R ), 0,1 );
|
||||
|
||||
/*
|
||||
color =
|
||||
// Ambient : simulates indirect lighting
|
||||
MaterialAmbientColor +
|
||||
// Diffuse : "color" of the object
|
||||
MaterialDiffuseColor * LightColor * LightPower * cosTheta / (distance*distance) +
|
||||
// Specular : reflective highlight, like a mirror
|
||||
MaterialSpecularColor * LightColor * LightPower * pow(cosAlpha,5) / (distance*distance);
|
||||
*/
|
||||
const vec3 bitShift3 = vec3(65536.0, 256.0, 1.0);
|
||||
const vec3 bitMask3 = vec3(0.0, 1.0/256.0, 1.0/256.0);
|
||||
float zNear = 0.1f; //- B / (1.0 - A);
|
||||
float zFar = 5000f;// B / (1.0 + A);
|
||||
float depthN = abs(EyeDirection_cameraspace.z - zNear)/128; // scale to a value in [0, 1]
|
||||
vec3 depthNPack3 = fract(depthN*bitShift3);
|
||||
depthNPack3 -= depthNPack3.xxy*bitMask3;
|
||||
|
||||
|
||||
float m = length(EyeDirection_cameraspace);
|
||||
m = 255 * clamp(dot(-EyeDirection_cameraspace, n)/length(EyeDirection_cameraspace), 0, 1);
|
||||
|
||||
float r = 128 * clamp(dot(n, vec3(0, 0, 1)), -1, 1) + 127;
|
||||
|
||||
float g = 128 * clamp(dot(n, vec3(0, 1, 0)), -1, 1) + 127;
|
||||
|
||||
float b = 128 * clamp(dot(n, vec3(1, 0, 0)), -1, 1) + 127;
|
||||
|
||||
//mist = vec3(m, m, m);
|
||||
mist = vec3(r, g, b);
|
||||
|
||||
}
|
|
@ -1,49 +0,0 @@
|
|||
#version 330 core
|
||||
|
||||
// Input vertex data, different for all executions of this shader.
|
||||
layout(location = 0) in vec3 vertexPosition_modelspace;
|
||||
layout(location = 1) in vec2 vertexUV;
|
||||
layout(location = 2) in vec3 vertexNormal_modelspace;
|
||||
|
||||
// Output data ; will be interpolated for each fragment.
|
||||
out vec2 UV;
|
||||
out vec3 Position_worldspace;
|
||||
out vec3 Normal_cameraspace;
|
||||
out vec3 EyeDirection_cameraspace;
|
||||
out vec3 LightDirection_cameraspace;
|
||||
|
||||
// Values that stay constant for the whole mesh.
|
||||
uniform mat4 MVP;
|
||||
uniform mat4 V;
|
||||
uniform mat4 M;
|
||||
uniform vec3 LightPosition_worldspace;
|
||||
|
||||
void main(){
|
||||
|
||||
// Output position of the vertex, in clip space : MVP * position
|
||||
gl_Position = MVP * vec4(vertexPosition_modelspace,1);
|
||||
|
||||
// Position of the vertex, in worldspace : M * position
|
||||
Position_worldspace = (M * vec4(vertexPosition_modelspace,1)).xyz;
|
||||
|
||||
// Vector that goes from the vertex to the camera, in camera space.
|
||||
// In camera space, the camera is at the origin (0,0,0).
|
||||
// Positive z
|
||||
EyeDirection_cameraspace = vec3(0,0,0) - ( V * M * vec4(vertexPosition_modelspace,1)).xyz;
|
||||
|
||||
// (hzyjerry) Cambria workaround to solve the pose mismatch issue
|
||||
float eye_z = EyeDirection_cameraspace[2];
|
||||
EyeDirection_cameraspace[2] = EyeDirection_cameraspace[1];
|
||||
EyeDirection_cameraspace[1] = -eye_z;
|
||||
|
||||
// Vector that goes from the vertex to the light, in camera space
|
||||
vec3 LightPosition_cameraspace = ( V * vec4(LightPosition_worldspace,1)).xyz;
|
||||
LightDirection_cameraspace = LightPosition_cameraspace + EyeDirection_cameraspace;
|
||||
|
||||
// Normal of the the vertex, in camera space
|
||||
Normal_cameraspace = ( M * vec4(vertexNormal_modelspace,0)).xyz; // Only correct if ModelMatrix does not scale the model ! Use its inverse transpose if not.
|
||||
|
||||
// UV of the vertex. No special space for this one.
|
||||
UV = vertexUV;
|
||||
}
|
||||
|
|
@ -1,13 +0,0 @@
|
|||
#version 330 core
|
||||
|
||||
// Input vertex data, different for all executions of this shader.
|
||||
layout(location = 0) in vec3 vertexPosition_modelspace;
|
||||
|
||||
// Output data ; will be interpolated for each fragment.
|
||||
out vec2 UV;
|
||||
|
||||
void main(){
|
||||
gl_Position = vec4(vertexPosition_modelspace,1);
|
||||
UV = (vertexPosition_modelspace.xy+vec2(1,1))/2.0;
|
||||
}
|
||||
|
|
@ -1,30 +0,0 @@
|
|||
#version 330 core
|
||||
|
||||
// Interpolated values from the vertex shaders
|
||||
in vec3 Position_worldspace;
|
||||
in vec3 Normal_cameraspace;
|
||||
in vec3 EyeDirection_cameraspace;
|
||||
in vec3 LightDirection_cameraspace;
|
||||
//flat in vec2 Semantics;
|
||||
flat in vec3 color;
|
||||
//flat in int semantic_layer;
|
||||
|
||||
|
||||
// Ouput data
|
||||
layout(location = 0) out vec3 out_color;
|
||||
|
||||
// Values that stay constant for the whole mesh.
|
||||
uniform sampler2DArray myTextureSampler;
|
||||
uniform mat4 MV;
|
||||
uniform vec3 LightPosition_worldspace;
|
||||
uniform int max_layer;
|
||||
|
||||
void main(){
|
||||
|
||||
//int layer = Semantics.x;
|
||||
|
||||
vec3 n = normalize( Normal_cameraspace );
|
||||
// Direction of the light (from the fragment to the light)
|
||||
|
||||
out_color = color;
|
||||
}
|
|
@ -1,58 +0,0 @@
|
|||
#version 330 core
|
||||
|
||||
// Input vertex data, different for all executions of this shader.
|
||||
layout(location = 0) in vec3 vertexPosition_modelspace;
|
||||
layout(location = 2) in vec3 vertexNormal_modelspace;
|
||||
layout(location = 3) in vec2 vertexSemantics;
|
||||
|
||||
|
||||
// Output data ; will be interpolated for each fragment.
|
||||
out vec3 Position_worldspace;
|
||||
out vec3 Normal_cameraspace;
|
||||
out vec3 EyeDirection_cameraspace;
|
||||
out vec3 LightDirection_cameraspace;
|
||||
//flat out vec2 Semantics;
|
||||
flat out vec3 color;
|
||||
//flat out int semantic_layer;
|
||||
|
||||
// Values that stay constant for the whole mesh.
|
||||
uniform sampler2DArray myTextureSampler;
|
||||
uniform mat4 MVP;
|
||||
uniform mat4 V;
|
||||
uniform mat4 M;
|
||||
uniform vec3 LightPosition_worldspace;
|
||||
uniform int max_layer;
|
||||
|
||||
void main(){
|
||||
|
||||
// Output position of the vertex, in clip space : MVP * position
|
||||
gl_Position = MVP * vec4(vertexPosition_modelspace,1);
|
||||
|
||||
// Position of the vertex, in worldspace : M * position
|
||||
Position_worldspace = (M * vec4(vertexPosition_modelspace,1)).xyz;
|
||||
|
||||
// Vector that goes from the vertex to the camera, in camera space.
|
||||
// In camera space, the camera is at the origin (0,0,0).
|
||||
// Positive z
|
||||
EyeDirection_cameraspace = vec3(0,0,0) - ( V * M * vec4(vertexPosition_modelspace,1)).xyz;
|
||||
|
||||
// (hzyjerry) Cambria workaround to solve the pose mismatch issue
|
||||
float eye_z = EyeDirection_cameraspace[2];
|
||||
EyeDirection_cameraspace[2] = EyeDirection_cameraspace[1];
|
||||
EyeDirection_cameraspace[1] = -eye_z;
|
||||
|
||||
// Vector that goes from the vertex to the light, in camera space
|
||||
vec3 LightPosition_cameraspace = ( V * vec4(LightPosition_worldspace,1)).xyz;
|
||||
LightDirection_cameraspace = LightPosition_cameraspace + EyeDirection_cameraspace;
|
||||
|
||||
// Normal of the the vertex, in camera space
|
||||
Normal_cameraspace = ( M * vec4(vertexNormal_modelspace,0)).xyz; // Only correct if ModelMatrix does not scale the model ! Use its inverse transpose if not.
|
||||
|
||||
// Semantic layer of the vertex
|
||||
//Semantics = vertexSemantics;
|
||||
float layer = vertexSemantics.x;
|
||||
color = texture( myTextureSampler, vec3(0, 0, layer)).rgb * 255.0;
|
||||
//color = vec3(layer, layer, layer);
|
||||
//semantic_layer = int(vertexSemantics.x);
|
||||
}
|
||||
|
|
@ -1,49 +0,0 @@
|
|||
#version 330 core
|
||||
|
||||
// Input vertex data, different for all executions of this shader.
|
||||
layout(location = 0) in vec3 vertexPosition_modelspace;
|
||||
layout(location = 1) in vec2 vertexUV;
|
||||
layout(location = 2) in vec3 vertexNormal_modelspace;
|
||||
|
||||
// Output data ; will be interpolated for each fragment.
|
||||
out vec2 UV;
|
||||
out vec3 Position_worldspace;
|
||||
out vec3 Normal_cameraspace;
|
||||
out vec3 EyeDirection_cameraspace;
|
||||
out vec3 LightDirection_cameraspace;
|
||||
|
||||
// Values that stay constant for the whole mesh.
|
||||
uniform mat4 MVP;
|
||||
uniform mat4 V;
|
||||
uniform mat4 M;
|
||||
uniform vec3 LightPosition_worldspace;
|
||||
|
||||
void main(){
|
||||
|
||||
// Output position of the vertex, in clip space : MVP * position
|
||||
gl_Position = MVP * vec4(vertexPosition_modelspace,1);
|
||||
|
||||
// Position of the vertex, in worldspace : M * position
|
||||
Position_worldspace = (M * vec4(vertexPosition_modelspace,1)).xyz;
|
||||
|
||||
// Vector that goes from the vertex to the camera, in camera space.
|
||||
// In camera space, the camera is at the origin (0,0,0).
|
||||
// Positive z
|
||||
EyeDirection_cameraspace = vec3(0,0,0) - ( V * M * vec4(vertexPosition_modelspace,1)).xyz;
|
||||
|
||||
// (hzyjerry) Cambria workaround to solve the pose mismatch issue
|
||||
float eye_z = EyeDirection_cameraspace[2];
|
||||
EyeDirection_cameraspace[2] = EyeDirection_cameraspace[1];
|
||||
EyeDirection_cameraspace[1] = -eye_z;
|
||||
|
||||
// Vector that goes from the vertex to the light, in camera space
|
||||
vec3 LightPosition_cameraspace = ( V * vec4(LightPosition_worldspace,1)).xyz;
|
||||
LightDirection_cameraspace = LightPosition_cameraspace + EyeDirection_cameraspace;
|
||||
|
||||
// Normal of the the vertex, in camera space
|
||||
Normal_cameraspace = ( V * M * vec4(vertexNormal_modelspace,0)).xyz; // Only correct if ModelMatrix does not scale the model ! Use its inverse transpose if not.
|
||||
|
||||
// UV of the vertex. No special space for this one.
|
||||
UV = vertexUV;
|
||||
}
|
||||
|
|
@ -1,44 +0,0 @@
|
|||
#version 330 core
|
||||
|
||||
in vec2 UV;
|
||||
|
||||
out vec3 color;
|
||||
|
||||
uniform sampler2D renderedTexture;
|
||||
uniform sampler2D myDepthTex;
|
||||
uniform float time;
|
||||
|
||||
void main(){
|
||||
//color = texture( renderedTexture, UV + 0.005*vec2( sin(time+1024.0*UV.x),cos(time+768.0*UV.y)) ).xyz ;
|
||||
//float t2 = texture(renderedTexture, UV).x * (1/512.0) * (128.0 / pow(2, 16));
|
||||
//float t2 = texture(renderedTexture, UV).x;
|
||||
//float t2 = pow(texture(renderedTexture, UV).x, 1);
|
||||
//color = vec3(t2, t2, t2);
|
||||
|
||||
float zNear = 0.1f;
|
||||
float zFar = 5000.0f;
|
||||
|
||||
const vec3 bitUnshift3 = vec3(1.0/65536.0, 1.0/256.0, 1.0);
|
||||
float z_e_mine = dot(texture2D(renderedTexture, UV).xyz, bitUnshift3);
|
||||
|
||||
//float z_e_mine = texture2D(renderedTexture, UV).x;
|
||||
|
||||
//z_e_mine = mix(zNear, zFar, z_e_mine); // scale from [0, 1] to [zNear, zFar]
|
||||
float z_e_ffun = texture2D(renderedTexture, UV).x;
|
||||
|
||||
//color = vec3(1, 1, 1);
|
||||
//color = vec3(z_e_ffun, z_e_ffun, z_e_ffun);
|
||||
//color = vec3(z_e_mine, z_e_mine, z_e_mine);
|
||||
color = vec3(5, 5, 5);
|
||||
|
||||
|
||||
// Unprojection part (deprecated)
|
||||
//color = (z_e_ffun <= 1)? vec3(0, 0, 0): vec3(1, 1, 1);
|
||||
|
||||
z_e_ffun = 2.0 * z_e_ffun - 1.0;
|
||||
z_e_ffun = 2.0 * zNear * zFar / (zFar + zNear - z_e_ffun * (zFar - zNear));
|
||||
//color = (z_e_ffun <= 3)? vec3(0, 0, 0): vec3(1, 1, 1);
|
||||
//color = vec3(z_e_ffun/10, z_e_ffun/10, z_e_ffun/10);
|
||||
//color = vec4(vec3(z_e_mine/zFar), 1.0); // divide by zFar to visualize;
|
||||
//color = vec3(z_e_ffun/zFar); // divide by zFar to visualize;
|
||||
}
|
|
@ -1,137 +0,0 @@
|
|||
import math
|
||||
|
||||
|
||||
def spherical_coordinates(i, j, w, h):
|
||||
""" Returns spherical coordinates of the pixel from the output image. """
|
||||
theta = 2*float(i)/float(w)-1
|
||||
phi = 2*float(j)/float(h)-1
|
||||
# phi = lat, theta = long
|
||||
return phi*(math.pi/2), theta*math.pi
|
||||
|
||||
|
||||
def vector_coordinates(phi, theta):
|
||||
""" Returns 3D vector which points to the pixel location inside a sphere. """
|
||||
return (math.cos(phi) * math.cos(theta), # X
|
||||
math.sin(phi), # Y
|
||||
math.cos(phi) * math.sin(theta)) # Z
|
||||
|
||||
|
||||
# Assign identifiers to the faces of the cube
|
||||
FACE_Z_POS = 1 # Left
|
||||
FACE_Z_NEG = 2 # Right
|
||||
FACE_Y_POS = 3 # Top
|
||||
FACE_Y_NEG = 4 # Bottom
|
||||
FACE_X_NEG = 5 # Front
|
||||
FACE_X_POS = 6 # Back
|
||||
|
||||
|
||||
def get_face(x, y, z):
|
||||
""" Uses 3D vector to find which cube face the pixel lies on. """
|
||||
largest_magnitude = max(abs(x), abs(y), abs(z))
|
||||
if largest_magnitude - abs(x) < 0.00001:
|
||||
return FACE_X_POS if x < 0 else FACE_X_NEG
|
||||
elif largest_magnitude - abs(y) < 0.00001:
|
||||
return FACE_Y_POS if y < 0 else FACE_Y_NEG
|
||||
elif largest_magnitude - abs(z) < 0.00001:
|
||||
return FACE_Z_POS if z < 0 else FACE_Z_NEG
|
||||
|
||||
|
||||
def raw_face_coordinates(face, x, y, z):
|
||||
"""
|
||||
Return coordinates with necessary sign (- or +) depending on which face they lie on.
|
||||
|
||||
From Open-GL specification (chapter 3.8.10) https://www.opengl.org/registry/doc/glspec41.core.20100725.pdf
|
||||
"""
|
||||
if face == FACE_X_NEG:
|
||||
xc = z
|
||||
yc = y
|
||||
ma = x
|
||||
return xc, yc, ma
|
||||
elif face == FACE_X_POS:
|
||||
xc = -z
|
||||
yc = y
|
||||
ma = x
|
||||
return xc, yc, ma
|
||||
elif face == FACE_Y_NEG:
|
||||
xc = z
|
||||
yc = -x
|
||||
ma = y
|
||||
return xc, yc, ma
|
||||
elif face == FACE_Y_POS:
|
||||
xc = z
|
||||
yc = x
|
||||
ma = y
|
||||
return xc, yc, ma
|
||||
elif face == FACE_Z_POS:
|
||||
xc = x
|
||||
yc = y
|
||||
ma = z
|
||||
return xc, yc, ma
|
||||
elif face == FACE_Z_NEG:
|
||||
xc = -x
|
||||
yc = y
|
||||
ma = z
|
||||
return xc, yc, ma
|
||||
|
||||
|
||||
def raw_coordinates(xc, yc, ma):
|
||||
""" Return 2D coordinates on the specified face relative to the bottom-left corner of the face. Also from Open-GL spec."""
|
||||
return (float(xc)/abs(float(ma)) + 1) / 2, (float(yc)/abs(float(ma)) + 1) / 2
|
||||
|
||||
|
||||
def face_origin_coordinates(face, n):
|
||||
""" Return bottom-left coordinate of specified face in the input image. """
|
||||
if face == FACE_X_NEG:
|
||||
return n, n
|
||||
elif face == FACE_X_POS:
|
||||
return 3*n, n
|
||||
elif face == FACE_Z_NEG:
|
||||
return 2*n, n
|
||||
elif face == FACE_Z_POS:
|
||||
return 0, n
|
||||
elif face == FACE_Y_POS:
|
||||
return n, 0
|
||||
elif face == FACE_Y_NEG:
|
||||
return n, 2*n
|
||||
|
||||
|
||||
def normalized_coordinates(face, x, y, n):
|
||||
""" Return pixel coordinates in the input image where the specified pixel lies. """
|
||||
face_coords = face_origin_coordinates(face, n)
|
||||
normalized_x = math.floor(x*n)
|
||||
normalized_y = math.floor(y*n)
|
||||
|
||||
# Stop out of bound behaviour
|
||||
if normalized_x < 0:
|
||||
normalized_x = 0
|
||||
elif normalized_x >= n:
|
||||
normalized_x = n-1
|
||||
if normalized_y < 0:
|
||||
normalized_x = 0
|
||||
elif normalized_y >= n:
|
||||
normalized_y = n-1
|
||||
|
||||
return face_coords[0] + normalized_x, face_coords[1] + normalized_y
|
||||
|
||||
|
||||
def find_corresponding_pixel(i, j, w, h, n):
|
||||
"""
|
||||
:param i: X coordinate of output image pixel
|
||||
:param j: Y coordinate of output image pixel
|
||||
:param w: Width of output image
|
||||
:param h: Height of output image
|
||||
:param n: Height/Width of each square face
|
||||
:return: Pixel coordinates for the input image that a specified pixel in the output image maps to.
|
||||
"""
|
||||
|
||||
spherical = spherical_coordinates(i, j, w, h)
|
||||
vector_coords = vector_coordinates(spherical[0], spherical[1])
|
||||
face = get_face(vector_coords[0], vector_coords[1], vector_coords[2])
|
||||
raw_face_coords = raw_face_coordinates(face, vector_coords[0], vector_coords[1], vector_coords[2])
|
||||
|
||||
cube_coords = raw_coordinates(raw_face_coords[0], raw_face_coords[1], raw_face_coords[2])
|
||||
|
||||
return normalized_coordinates(face, cube_coords[0], cube_coords[1], n)
|
||||
|
||||
|
||||
|
File diff suppressed because it is too large
Load Diff
|
@ -1,151 +0,0 @@
|
|||
// Include standard headers
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <vector>
|
||||
#include <string>
|
||||
#include <fstream>
|
||||
#include <iostream>
|
||||
#include <cstdlib> //rand
|
||||
#include <chrono>
|
||||
#include "boost/multi_array.hpp"
|
||||
#include "boost/timer.hpp"
|
||||
|
||||
|
||||
#include <glad/egl.h>
|
||||
#include <glad/gl.h>
|
||||
#include "lodepng.h"
|
||||
|
||||
#include <glm/glm.hpp>
|
||||
#include <glm/gtc/matrix_transform.hpp>
|
||||
#include <glm/gtx/transform.hpp>
|
||||
#include <glm/gtc/quaternion.hpp>
|
||||
#include <glm/gtx/quaternion.hpp>
|
||||
|
||||
using namespace std;
|
||||
|
||||
#include <common/shader.hpp>
|
||||
#include <common/texture.hpp>
|
||||
#include <common/objloader.hpp>
|
||||
#include <common/vboindexer.hpp>
|
||||
#include <common/cmdline.h>
|
||||
#include <common/controls.hpp>
|
||||
#include <common/semantic_color.hpp>
|
||||
|
||||
#include <common/MTLobjloader.hpp>
|
||||
#include <common/MTLplyloader.hpp>
|
||||
#include <common/MTLtexture.hpp>
|
||||
#include <zmq.hpp>
|
||||
|
||||
#ifndef _WIN32
|
||||
#include <unistd.h>
|
||||
#else
|
||||
#include <windows.h>
|
||||
#define sleep(n) Sleep(n)
|
||||
#endif
|
||||
|
||||
|
||||
int main( int argc, char * argv[] )
|
||||
{
|
||||
|
||||
cmdline::parser cmdp;
|
||||
cmdp.add<std::string>("modelpath", 'd', "data model directory", true, "");
|
||||
cmdp.add<int>("Semantic Source", 'r', "Semantic data source", false, 1);
|
||||
cmdp.add<int>("Port", 'p', "Semantic loading port", false, 5055);
|
||||
|
||||
cmdp.parse_check(argc, argv);
|
||||
|
||||
std::string model_path = cmdp.get<std::string>("modelpath");
|
||||
int port = cmdp.get<int>("Port");
|
||||
int semantic_src = cmdp.get<int>("Semantic Source");
|
||||
int ply;
|
||||
|
||||
std::string name_obj = model_path + "/mesh.obj";
|
||||
name_obj = model_path + "/semantic.obj";
|
||||
if (semantic_src == 1) ply = 0;
|
||||
if (semantic_src == 2) ply = 1;
|
||||
|
||||
std::vector<std::vector<glm::vec3>> mtl_vertices;
|
||||
std::vector<std::vector<glm::vec2>> mtl_uvs;
|
||||
std::vector<std::vector<glm::vec3>> mtl_normals;
|
||||
std::vector<glm::vec3> mtl_sem_centers;
|
||||
std::vector<std::string> material_name;
|
||||
std::vector<int> material_id;
|
||||
std::string mtllib;
|
||||
|
||||
std::vector<glm::vec3> vertices;
|
||||
std::vector<glm::vec2> uvs;
|
||||
std::vector<glm::vec3> normals;
|
||||
std::vector<TextureObj> TextObj;
|
||||
unsigned int num_layers;
|
||||
|
||||
/* initialize random seed: */
|
||||
srand (0);
|
||||
|
||||
bool res;
|
||||
int num_vertices;
|
||||
if (ply > 0) {
|
||||
res = loadPLY_MTL(model_path.c_str(), mtl_vertices, mtl_uvs, mtl_normals, mtl_sem_centers, material_id, mtllib, num_vertices);
|
||||
printf("From ply loaded total of %d vertices\n", num_vertices);
|
||||
} else {
|
||||
res = loadOBJ_MTL(name_obj.c_str(), mtl_vertices, mtl_uvs, mtl_normals, mtl_sem_centers, material_name, mtllib);
|
||||
for (int i = 0; i < 20; i++) {
|
||||
printf("Loaded semantic center %f, %f, %f\n", mtl_sem_centers[i].x, mtl_sem_centers[i].y, mtl_sem_centers[i].z);
|
||||
}
|
||||
}
|
||||
if (res == false) { printf("Was not able to load the semantic.obj file.\n"); exit(-1); }
|
||||
else { printf("Semantic.obj file was loaded with success.\n"); }
|
||||
|
||||
// Load the textures
|
||||
std::string mtl_path = model_path + "/" + mtllib;
|
||||
bool MTL_loaded;
|
||||
if (ply > 0) {
|
||||
mtl_path = model_path;
|
||||
MTL_loaded = loadPLYtextures(TextObj, material_id);
|
||||
} else {
|
||||
MTL_loaded = loadMTLtextures(mtl_path, TextObj, material_name);
|
||||
}
|
||||
if (MTL_loaded == false) { printf("Was not able to load textures\n"); exit(-1); }
|
||||
else { printf("Texture file was loaded with success, total: %lu\n", TextObj.size()); }
|
||||
|
||||
// Read our .obj file
|
||||
// Note: use unsigned int because of too many indices
|
||||
std::vector<unsigned int> indices;
|
||||
std::vector<glm::vec3> indexed_vertices;
|
||||
std::vector<glm::vec2> indexed_uvs;
|
||||
std::vector<glm::vec3> indexed_normals;
|
||||
std::vector<glm::vec2> indexed_semantics;
|
||||
|
||||
/*
|
||||
indexVBO_MTL(mtl_vertices, mtl_uvs, mtl_normals, indices, indexed_vertices, indexed_uvs, indexed_normals, indexed_semantics);
|
||||
std::cout << "Finished indexing vertices v " << indexed_vertices.size() << " uvs " << indexed_uvs.size() << " normals " << indexed_normals.size() << " semantics " << indexed_semantics.size() << std::endl;
|
||||
std::cout << "Semantics ";
|
||||
std::cout << std::endl;
|
||||
*/
|
||||
|
||||
zmq::context_t context (1);
|
||||
zmq::socket_t socket (context, ZMQ_REP);
|
||||
zmq::message_t request;
|
||||
socket.bind ("tcp://127.0.0.1:" + std::to_string(port));
|
||||
|
||||
// Wait for next request from client
|
||||
socket.recv (&request);
|
||||
std::string request_str = std::string(static_cast<char*>(request.data()), request.size());
|
||||
|
||||
|
||||
int dim = 3;
|
||||
int message_sz = mtl_sem_centers.size()*sizeof(float)*dim;
|
||||
zmq::message_t reply (message_sz);
|
||||
|
||||
float * reply_data_handle = (float*)reply.data();
|
||||
for (int i = 0; i < mtl_sem_centers.size(); i++) {
|
||||
for (int k = 0; k < dim; k++) {
|
||||
int offset = k;
|
||||
float tmp_float = mtl_sem_centers[i][k];
|
||||
reply_data_handle[offset + i * dim] = tmp_float;
|
||||
}
|
||||
}
|
||||
|
||||
socket.send (reply);
|
||||
|
||||
return 0;
|
||||
}
|
|
@ -1,41 +0,0 @@
|
|||
add_definitions(
|
||||
-DTW_STATIC
|
||||
-DTW_NO_LIB_PRAGMA
|
||||
-DTW_NO_DIRECT3D
|
||||
-DGLEW_STATIC
|
||||
-D_CRT_SECURE_NO_WARNINGS
|
||||
)
|
||||
|
||||
### GLFW ###
|
||||
add_subdirectory (glfw-3.1.2)
|
||||
|
||||
if(${CMAKE_SYSTEM_NAME} MATCHES "Linux")
|
||||
set(OPENGL_LIBRARY
|
||||
${OPENGL_LIBRARY}
|
||||
-lGL -lGLU -lXrandr -lXext -lX11 -lrt
|
||||
${CMAKE_DL_LIBS}
|
||||
${GLFW_LIBRARIES}
|
||||
)
|
||||
elseif(${CMAKE_SYSTEM_NAME} MATCHES "Darwin")
|
||||
set(OPENGL_LIBRARY
|
||||
${OPENGL_LIBRARY}
|
||||
${CMAKE_DL_LIBS}
|
||||
${GLFW_LIBRARIES}
|
||||
)
|
||||
endif(${CMAKE_SYSTEM_NAME} MATCHES "Linux")
|
||||
|
||||
### GLEW ###
|
||||
|
||||
set(GLEW_SOURCE
|
||||
glew.c
|
||||
)
|
||||
|
||||
|
||||
add_library( GLEW_1130 SHARED
|
||||
${GLEW_SOURCE}
|
||||
${GLEW_INCLUDE}
|
||||
)
|
||||
|
||||
target_link_libraries(GLEW_1130
|
||||
${OPENGL_LIBRARY}
|
||||
)
|
|
@ -1,3 +0,0 @@
|
|||
wget https://github.com/glfw/glfw/releases/download/3.1.2/glfw-3.1.2.zip
|
||||
unzip glfw-3.1.2.zip
|
||||
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
|
@ -1,160 +0,0 @@
|
|||
#ifndef __eglplatform_h_
|
||||
#define __eglplatform_h_
|
||||
|
||||
/*
|
||||
** Copyright (c) 2007-2016 The Khronos Group Inc.
|
||||
**
|
||||
** Permission is hereby granted, free of charge, to any person obtaining a
|
||||
** copy of this software and/or associated documentation files (the
|
||||
** "Materials"), to deal in the Materials without restriction, including
|
||||
** without limitation the rights to use, copy, modify, merge, publish,
|
||||
** distribute, sublicense, and/or sell copies of the Materials, and to
|
||||
** permit persons to whom the Materials are furnished to do so, subject to
|
||||
** the following conditions:
|
||||
**
|
||||
** The above copyright notice and this permission notice shall be included
|
||||
** in all copies or substantial portions of the Materials.
|
||||
**
|
||||
** THE MATERIALS ARE PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||
** EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||
** MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
|
||||
** IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
|
||||
** CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
|
||||
** TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
|
||||
** MATERIALS OR THE USE OR OTHER DEALINGS IN THE MATERIALS.
|
||||
*/
|
||||
|
||||
/* Platform-specific types and definitions for egl.h
|
||||
* $Revision: 30994 $ on $Date: 2015-04-30 13:36:48 -0700 (Thu, 30 Apr 2015) $
|
||||
*
|
||||
* Adopters may modify khrplatform.h and this file to suit their platform.
|
||||
* You are encouraged to submit all modifications to the Khronos group so that
|
||||
* they can be included in future versions of this file. Please submit changes
|
||||
* by sending them to the public Khronos Bugzilla (http://khronos.org/bugzilla)
|
||||
* by filing a bug against product "EGL" component "Registry".
|
||||
*/
|
||||
|
||||
#include <KHR/khrplatform.h>
|
||||
|
||||
/* Macros used in EGL function prototype declarations.
|
||||
*
|
||||
* EGL functions should be prototyped as:
|
||||
*
|
||||
* EGLAPI return-type EGLAPIENTRY eglFunction(arguments);
|
||||
* typedef return-type (EXPAPIENTRYP PFNEGLFUNCTIONPROC) (arguments);
|
||||
*
|
||||
* KHRONOS_APICALL and KHRONOS_APIENTRY are defined in KHR/khrplatform.h
|
||||
*/
|
||||
|
||||
#ifndef EGLAPI
|
||||
#define EGLAPI KHRONOS_APICALL
|
||||
#endif
|
||||
|
||||
#ifndef EGLAPIENTRY
|
||||
#define EGLAPIENTRY KHRONOS_APIENTRY
|
||||
#endif
|
||||
#define EGLAPIENTRYP EGLAPIENTRY*
|
||||
|
||||
/* The types NativeDisplayType, NativeWindowType, and NativePixmapType
|
||||
* are aliases of window-system-dependent types, such as X Display * or
|
||||
* Windows Device Context. They must be defined in platform-specific
|
||||
* code below. The EGL-prefixed versions of Native*Type are the same
|
||||
* types, renamed in EGL 1.3 so all types in the API start with "EGL".
|
||||
*
|
||||
* Khronos STRONGLY RECOMMENDS that you use the default definitions
|
||||
* provided below, since these changes affect both binary and source
|
||||
* portability of applications using EGL running on different EGL
|
||||
* implementations.
|
||||
*/
|
||||
|
||||
#if defined(_WIN32) || defined(__VC32__) && !defined(__CYGWIN__) && !defined(__SCITECH_SNAP__) /* Win32 and WinCE */
|
||||
#ifndef WIN32_LEAN_AND_MEAN
|
||||
#define WIN32_LEAN_AND_MEAN 1
|
||||
#endif
|
||||
#include <windows.h>
|
||||
|
||||
typedef HDC EGLNativeDisplayType;
|
||||
typedef HBITMAP EGLNativePixmapType;
|
||||
typedef HWND EGLNativeWindowType;
|
||||
|
||||
#elif defined(__WINSCW__) || defined(__SYMBIAN32__) /* Symbian */
|
||||
|
||||
typedef int EGLNativeDisplayType;
|
||||
typedef void *EGLNativeWindowType;
|
||||
typedef void *EGLNativePixmapType;
|
||||
|
||||
#elif defined(WL_EGL_PLATFORM)
|
||||
|
||||
typedef struct wl_display *EGLNativeDisplayType;
|
||||
typedef struct wl_egl_pixmap *EGLNativePixmapType;
|
||||
typedef struct wl_egl_window *EGLNativeWindowType;
|
||||
|
||||
#elif defined(__GBM__)
|
||||
|
||||
typedef struct gbm_device *EGLNativeDisplayType;
|
||||
typedef struct gbm_bo *EGLNativePixmapType;
|
||||
typedef void *EGLNativeWindowType;
|
||||
|
||||
#elif defined(__ANDROID__) || defined(ANDROID)
|
||||
|
||||
struct ANativeWindow;
|
||||
struct egl_native_pixmap_t;
|
||||
|
||||
typedef struct ANativeWindow* EGLNativeWindowType;
|
||||
typedef struct egl_native_pixmap_t* EGLNativePixmapType;
|
||||
typedef void* EGLNativeDisplayType;
|
||||
|
||||
#elif defined(__unix__) || defined(__APPLE__)
|
||||
|
||||
#if defined(MESA_EGL_NO_X11_HEADERS)
|
||||
|
||||
typedef void *EGLNativeDisplayType;
|
||||
typedef khronos_uintptr_t EGLNativePixmapType;
|
||||
typedef khronos_uintptr_t EGLNativeWindowType;
|
||||
|
||||
#else
|
||||
|
||||
/* X11 (tentative) */
|
||||
#include <X11/Xlib.h>
|
||||
#include <X11/Xutil.h>
|
||||
|
||||
typedef Display *EGLNativeDisplayType;
|
||||
typedef Pixmap EGLNativePixmapType;
|
||||
typedef Window EGLNativeWindowType;
|
||||
|
||||
#endif /* MESA_EGL_NO_X11_HEADERS */
|
||||
|
||||
#elif __HAIKU__
|
||||
#include <kernel/image.h>
|
||||
typedef void *EGLNativeDisplayType;
|
||||
typedef khronos_uintptr_t EGLNativePixmapType;
|
||||
typedef khronos_uintptr_t EGLNativeWindowType;
|
||||
|
||||
#else
|
||||
#error "Platform not recognized"
|
||||
#endif
|
||||
|
||||
/* EGL 1.2 types, renamed for consistency in EGL 1.3 */
|
||||
typedef EGLNativeDisplayType NativeDisplayType;
|
||||
typedef EGLNativePixmapType NativePixmapType;
|
||||
typedef EGLNativeWindowType NativeWindowType;
|
||||
|
||||
|
||||
/* Define EGLint. This must be a signed integral type large enough to contain
|
||||
* all legal attribute names and values passed into and out of EGL, whether
|
||||
* their type is boolean, bitmask, enumerant (symbolic constant), integer,
|
||||
* handle, or other. While in general a 32-bit integer will suffice, if
|
||||
* handles are 64 bit types, then EGLint should be defined as a signed 64-bit
|
||||
* integer type.
|
||||
*/
|
||||
typedef khronos_int32_t EGLint;
|
||||
|
||||
|
||||
/* C++ / C typecast macros for special EGL handle values */
|
||||
#if defined(__cplusplus)
|
||||
#define EGL_CAST(type, value) (static_cast<type>(value))
|
||||
#else
|
||||
#define EGL_CAST(type, value) ((type) (value))
|
||||
#endif
|
||||
|
||||
#endif /* __eglplatform_h */
|
|
@ -1,284 +0,0 @@
|
|||
#ifndef __khrplatform_h_
|
||||
#define __khrplatform_h_
|
||||
|
||||
/*
|
||||
** Copyright (c) 2008-2009 The Khronos Group Inc.
|
||||
**
|
||||
** Permission is hereby granted, free of charge, to any person obtaining a
|
||||
** copy of this software and/or associated documentation files (the
|
||||
** "Materials"), to deal in the Materials without restriction, including
|
||||
** without limitation the rights to use, copy, modify, merge, publish,
|
||||
** distribute, sublicense, and/or sell copies of the Materials, and to
|
||||
** permit persons to whom the Materials are furnished to do so, subject to
|
||||
** the following conditions:
|
||||
**
|
||||
** The above copyright notice and this permission notice shall be included
|
||||
** in all copies or substantial portions of the Materials.
|
||||
**
|
||||
** THE MATERIALS ARE PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||
** EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||
** MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
|
||||
** IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
|
||||
** CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
|
||||
** TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
|
||||
** MATERIALS OR THE USE OR OTHER DEALINGS IN THE MATERIALS.
|
||||
*/
|
||||
|
||||
/* Khronos platform-specific types and definitions.
|
||||
*
|
||||
* $Revision: 32517 $ on $Date: 2016-03-11 02:41:19 -0800 (Fri, 11 Mar 2016) $
|
||||
*
|
||||
* Adopters may modify this file to suit their platform. Adopters are
|
||||
* encouraged to submit platform specific modifications to the Khronos
|
||||
* group so that they can be included in future versions of this file.
|
||||
* Please submit changes by sending them to the public Khronos Bugzilla
|
||||
* (http://khronos.org/bugzilla) by filing a bug against product
|
||||
* "Khronos (general)" component "Registry".
|
||||
*
|
||||
* A predefined template which fills in some of the bug fields can be
|
||||
* reached using http://tinyurl.com/khrplatform-h-bugreport, but you
|
||||
* must create a Bugzilla login first.
|
||||
*
|
||||
*
|
||||
* See the Implementer's Guidelines for information about where this file
|
||||
* should be located on your system and for more details of its use:
|
||||
* http://www.khronos.org/registry/implementers_guide.pdf
|
||||
*
|
||||
* This file should be included as
|
||||
* #include <KHR/khrplatform.h>
|
||||
* by Khronos client API header files that use its types and defines.
|
||||
*
|
||||
* The types in khrplatform.h should only be used to define API-specific types.
|
||||
*
|
||||
* Types defined in khrplatform.h:
|
||||
* khronos_int8_t signed 8 bit
|
||||
* khronos_uint8_t unsigned 8 bit
|
||||
* khronos_int16_t signed 16 bit
|
||||
* khronos_uint16_t unsigned 16 bit
|
||||
* khronos_int32_t signed 32 bit
|
||||
* khronos_uint32_t unsigned 32 bit
|
||||
* khronos_int64_t signed 64 bit
|
||||
* khronos_uint64_t unsigned 64 bit
|
||||
* khronos_intptr_t signed same number of bits as a pointer
|
||||
* khronos_uintptr_t unsigned same number of bits as a pointer
|
||||
* khronos_ssize_t signed size
|
||||
* khronos_usize_t unsigned size
|
||||
* khronos_float_t signed 32 bit floating point
|
||||
* khronos_time_ns_t unsigned 64 bit time in nanoseconds
|
||||
* khronos_utime_nanoseconds_t unsigned time interval or absolute time in
|
||||
* nanoseconds
|
||||
* khronos_stime_nanoseconds_t signed time interval in nanoseconds
|
||||
* khronos_boolean_enum_t enumerated boolean type. This should
|
||||
* only be used as a base type when a client API's boolean type is
|
||||
* an enum. Client APIs which use an integer or other type for
|
||||
* booleans cannot use this as the base type for their boolean.
|
||||
*
|
||||
* Tokens defined in khrplatform.h:
|
||||
*
|
||||
* KHRONOS_FALSE, KHRONOS_TRUE Enumerated boolean false/true values.
|
||||
*
|
||||
* KHRONOS_SUPPORT_INT64 is 1 if 64 bit integers are supported; otherwise 0.
|
||||
* KHRONOS_SUPPORT_FLOAT is 1 if floats are supported; otherwise 0.
|
||||
*
|
||||
* Calling convention macros defined in this file:
|
||||
* KHRONOS_APICALL
|
||||
* KHRONOS_APIENTRY
|
||||
* KHRONOS_APIATTRIBUTES
|
||||
*
|
||||
* These may be used in function prototypes as:
|
||||
*
|
||||
* KHRONOS_APICALL void KHRONOS_APIENTRY funcname(
|
||||
* int arg1,
|
||||
* int arg2) KHRONOS_APIATTRIBUTES;
|
||||
*/
|
||||
|
||||
/*-------------------------------------------------------------------------
|
||||
* Definition of KHRONOS_APICALL
|
||||
*-------------------------------------------------------------------------
|
||||
* This precedes the return type of the function in the function prototype.
|
||||
*/
|
||||
#if defined(_WIN32) && !defined(__SCITECH_SNAP__)
|
||||
# define KHRONOS_APICALL __declspec(dllimport)
|
||||
#elif defined (__SYMBIAN32__)
|
||||
# define KHRONOS_APICALL IMPORT_C
|
||||
#elif defined(__ANDROID__)
|
||||
# define KHRONOS_APICALL __attribute__((visibility("default")))
|
||||
#else
|
||||
# define KHRONOS_APICALL
|
||||
#endif
|
||||
|
||||
/*-------------------------------------------------------------------------
|
||||
* Definition of KHRONOS_APIENTRY
|
||||
*-------------------------------------------------------------------------
|
||||
* This follows the return type of the function and precedes the function
|
||||
* name in the function prototype.
|
||||
*/
|
||||
#if defined(_WIN32) && !defined(_WIN32_WCE) && !defined(__SCITECH_SNAP__)
|
||||
/* Win32 but not WinCE */
|
||||
# define KHRONOS_APIENTRY __stdcall
|
||||
#else
|
||||
# define KHRONOS_APIENTRY
|
||||
#endif
|
||||
|
||||
/*-------------------------------------------------------------------------
|
||||
* Definition of KHRONOS_APIATTRIBUTES
|
||||
*-------------------------------------------------------------------------
|
||||
* This follows the closing parenthesis of the function prototype arguments.
|
||||
*/
|
||||
#if defined (__ARMCC_2__)
|
||||
#define KHRONOS_APIATTRIBUTES __softfp
|
||||
#else
|
||||
#define KHRONOS_APIATTRIBUTES
|
||||
#endif
|
||||
|
||||
/*-------------------------------------------------------------------------
|
||||
* basic type definitions
|
||||
*-----------------------------------------------------------------------*/
|
||||
#if (defined(__STDC_VERSION__) && __STDC_VERSION__ >= 199901L) || defined(__GNUC__) || defined(__SCO__) || defined(__USLC__)
|
||||
|
||||
|
||||
/*
|
||||
* Using <stdint.h>
|
||||
*/
|
||||
#include <stdint.h>
|
||||
typedef int32_t khronos_int32_t;
|
||||
typedef uint32_t khronos_uint32_t;
|
||||
typedef int64_t khronos_int64_t;
|
||||
typedef uint64_t khronos_uint64_t;
|
||||
#define KHRONOS_SUPPORT_INT64 1
|
||||
#define KHRONOS_SUPPORT_FLOAT 1
|
||||
|
||||
#elif defined(__VMS ) || defined(__sgi)
|
||||
|
||||
/*
|
||||
* Using <inttypes.h>
|
||||
*/
|
||||
#include <inttypes.h>
|
||||
typedef int32_t khronos_int32_t;
|
||||
typedef uint32_t khronos_uint32_t;
|
||||
typedef int64_t khronos_int64_t;
|
||||
typedef uint64_t khronos_uint64_t;
|
||||
#define KHRONOS_SUPPORT_INT64 1
|
||||
#define KHRONOS_SUPPORT_FLOAT 1
|
||||
|
||||
#elif defined(_WIN32) && !defined(__SCITECH_SNAP__)
|
||||
|
||||
/*
|
||||
* Win32
|
||||
*/
|
||||
typedef __int32 khronos_int32_t;
|
||||
typedef unsigned __int32 khronos_uint32_t;
|
||||
typedef __int64 khronos_int64_t;
|
||||
typedef unsigned __int64 khronos_uint64_t;
|
||||
#define KHRONOS_SUPPORT_INT64 1
|
||||
#define KHRONOS_SUPPORT_FLOAT 1
|
||||
|
||||
#elif defined(__sun__) || defined(__digital__)
|
||||
|
||||
/*
|
||||
* Sun or Digital
|
||||
*/
|
||||
typedef int khronos_int32_t;
|
||||
typedef unsigned int khronos_uint32_t;
|
||||
#if defined(__arch64__) || defined(_LP64)
|
||||
typedef long int khronos_int64_t;
|
||||
typedef unsigned long int khronos_uint64_t;
|
||||
#else
|
||||
typedef long long int khronos_int64_t;
|
||||
typedef unsigned long long int khronos_uint64_t;
|
||||
#endif /* __arch64__ */
|
||||
#define KHRONOS_SUPPORT_INT64 1
|
||||
#define KHRONOS_SUPPORT_FLOAT 1
|
||||
|
||||
#elif 0
|
||||
|
||||
/*
|
||||
* Hypothetical platform with no float or int64 support
|
||||
*/
|
||||
typedef int khronos_int32_t;
|
||||
typedef unsigned int khronos_uint32_t;
|
||||
#define KHRONOS_SUPPORT_INT64 0
|
||||
#define KHRONOS_SUPPORT_FLOAT 0
|
||||
|
||||
#else
|
||||
|
||||
/*
|
||||
* Generic fallback
|
||||
*/
|
||||
#include <stdint.h>
|
||||
typedef int32_t khronos_int32_t;
|
||||
typedef uint32_t khronos_uint32_t;
|
||||
typedef int64_t khronos_int64_t;
|
||||
typedef uint64_t khronos_uint64_t;
|
||||
#define KHRONOS_SUPPORT_INT64 1
|
||||
#define KHRONOS_SUPPORT_FLOAT 1
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
/*
|
||||
* Types that are (so far) the same on all platforms
|
||||
*/
|
||||
typedef signed char khronos_int8_t;
|
||||
typedef unsigned char khronos_uint8_t;
|
||||
typedef signed short int khronos_int16_t;
|
||||
typedef unsigned short int khronos_uint16_t;
|
||||
|
||||
/*
|
||||
* Types that differ between LLP64 and LP64 architectures - in LLP64,
|
||||
* pointers are 64 bits, but 'long' is still 32 bits. Win64 appears
|
||||
* to be the only LLP64 architecture in current use.
|
||||
*/
|
||||
#ifdef _WIN64
|
||||
typedef signed long long int khronos_intptr_t;
|
||||
typedef unsigned long long int khronos_uintptr_t;
|
||||
typedef signed long long int khronos_ssize_t;
|
||||
typedef unsigned long long int khronos_usize_t;
|
||||
#else
|
||||
typedef signed long int khronos_intptr_t;
|
||||
typedef unsigned long int khronos_uintptr_t;
|
||||
typedef signed long int khronos_ssize_t;
|
||||
typedef unsigned long int khronos_usize_t;
|
||||
#endif
|
||||
|
||||
#if KHRONOS_SUPPORT_FLOAT
|
||||
/*
|
||||
* Float type
|
||||
*/
|
||||
typedef float khronos_float_t;
|
||||
#endif
|
||||
|
||||
#if KHRONOS_SUPPORT_INT64
|
||||
/* Time types
|
||||
*
|
||||
* These types can be used to represent a time interval in nanoseconds or
|
||||
* an absolute Unadjusted System Time. Unadjusted System Time is the number
|
||||
* of nanoseconds since some arbitrary system event (e.g. since the last
|
||||
* time the system booted). The Unadjusted System Time is an unsigned
|
||||
* 64 bit value that wraps back to 0 every 584 years. Time intervals
|
||||
* may be either signed or unsigned.
|
||||
*/
|
||||
typedef khronos_uint64_t khronos_utime_nanoseconds_t;
|
||||
typedef khronos_int64_t khronos_stime_nanoseconds_t;
|
||||
#endif
|
||||
|
||||
/*
|
||||
* Dummy value used to pad enum types to 32 bits.
|
||||
*/
|
||||
#ifndef KHRONOS_MAX_ENUM
|
||||
#define KHRONOS_MAX_ENUM 0x7FFFFFFF
|
||||
#endif
|
||||
|
||||
/*
|
||||
* Enumerated boolean type
|
||||
*
|
||||
* Values other than zero should be considered to be true. Therefore
|
||||
* comparisons should not be made against KHRONOS_TRUE.
|
||||
*/
|
||||
typedef enum {
|
||||
KHRONOS_FALSE = 0,
|
||||
KHRONOS_TRUE = 1,
|
||||
KHRONOS_BOOLEAN_ENUM_FORCE_SIZE = KHRONOS_MAX_ENUM
|
||||
} khronos_boolean_enum_t;
|
||||
|
||||
#endif /* __khrplatform_h_ */
|
|
@ -1,422 +0,0 @@
|
|||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <glad/egl.h>
|
||||
|
||||
#ifndef GLAD_IMPL_UTIL_C_
|
||||
#define GLAD_IMPL_UTIL_C_
|
||||
|
||||
#if _MSC_VER >= 1400
|
||||
#define GLAD_IMPL_UTIL_STRNCPY(dest, source, len) strncpy_s(dest, len, source, len-1);
|
||||
#else
|
||||
#define GLAD_IMPL_UTIL_STRNCPY(dest, source, len) strncpy(dest, source, len);
|
||||
#endif
|
||||
|
||||
#ifdef _MSC_VER
|
||||
#define GLAD_IMPL_UTIL_SSCANF sscanf_s
|
||||
#else
|
||||
#define GLAD_IMPL_UTIL_SSCANF sscanf
|
||||
#endif
|
||||
|
||||
#endif /* GLAD_IMPL_UTIL_C_ */
|
||||
|
||||
|
||||
int GLAD_EGL_VERSION_1_0;
|
||||
int GLAD_EGL_VERSION_1_1;
|
||||
int GLAD_EGL_VERSION_1_2;
|
||||
int GLAD_EGL_VERSION_1_3;
|
||||
int GLAD_EGL_VERSION_1_4;
|
||||
int GLAD_EGL_VERSION_1_5;
|
||||
int GLAD_EGL_EXT_platform_device;
|
||||
int GLAD_EGL_EXT_platform_base;
|
||||
int GLAD_EGL_NV_device_cuda;
|
||||
int GLAD_EGL_EXT_device_enumeration;
|
||||
int GLAD_EGL_EXT_device_query;
|
||||
int GLAD_EGL_EXT_device_base;
|
||||
int GLAD_EGL_NV_cuda_event;
|
||||
|
||||
|
||||
|
||||
PFNEGLQUERYDEVICESEXTPROC glad_eglQueryDevicesEXT;
|
||||
PFNEGLCREATEPBUFFERSURFACEPROC glad_eglCreatePbufferSurface;
|
||||
PFNEGLGETERRORPROC glad_eglGetError;
|
||||
PFNEGLGETPROCADDRESSPROC glad_eglGetProcAddress;
|
||||
PFNEGLGETCURRENTDISPLAYPROC glad_eglGetCurrentDisplay;
|
||||
PFNEGLQUERYAPIPROC glad_eglQueryAPI;
|
||||
PFNEGLCREATEPLATFORMPIXMAPSURFACEPROC glad_eglCreatePlatformPixmapSurface;
|
||||
PFNEGLQUERYDISPLAYATTRIBKHRPROC glad_eglQueryDisplayAttribKHR;
|
||||
PFNEGLDESTROYSYNCPROC glad_eglDestroySync;
|
||||
PFNEGLCREATEIMAGEPROC glad_eglCreateImage;
|
||||
PFNEGLQUERYCONTEXTPROC glad_eglQueryContext;
|
||||
PFNEGLSWAPBUFFERSPROC glad_eglSwapBuffers;
|
||||
PFNEGLCREATECONTEXTPROC glad_eglCreateContext;
|
||||
PFNEGLCHOOSECONFIGPROC glad_eglChooseConfig;
|
||||
PFNEGLBINDAPIPROC glad_eglBindAPI;
|
||||
PFNEGLWAITNATIVEPROC glad_eglWaitNative;
|
||||
PFNEGLTERMINATEPROC glad_eglTerminate;
|
||||
PFNEGLCREATEPLATFORMPIXMAPSURFACEEXTPROC glad_eglCreatePlatformPixmapSurfaceEXT;
|
||||
PFNEGLRELEASETHREADPROC glad_eglReleaseThread;
|
||||
PFNEGLCREATEPLATFORMWINDOWSURFACEPROC glad_eglCreatePlatformWindowSurface;
|
||||
PFNEGLGETCONFIGATTRIBPROC glad_eglGetConfigAttrib;
|
||||
PFNEGLGETCURRENTSURFACEPROC glad_eglGetCurrentSurface;
|
||||
PFNEGLCOPYBUFFERSPROC glad_eglCopyBuffers;
|
||||
PFNEGLGETPLATFORMDISPLAYEXTPROC glad_eglGetPlatformDisplayEXT;
|
||||
PFNEGLQUERYDEVICEATTRIBEXTPROC glad_eglQueryDeviceAttribEXT;
|
||||
PFNEGLCREATEPIXMAPSURFACEPROC glad_eglCreatePixmapSurface;
|
||||
PFNEGLBINDTEXIMAGEPROC glad_eglBindTexImage;
|
||||
PFNEGLGETPLATFORMDISPLAYPROC glad_eglGetPlatformDisplay;
|
||||
PFNEGLGETDISPLAYPROC glad_eglGetDisplay;
|
||||
PFNEGLQUERYSTRINGPROC glad_eglQueryString;
|
||||
PFNEGLCLIENTWAITSYNCPROC glad_eglClientWaitSync;
|
||||
PFNEGLWAITSYNCPROC glad_eglWaitSync;
|
||||
PFNEGLDESTROYIMAGEPROC glad_eglDestroyImage;
|
||||
PFNEGLRELEASETEXIMAGEPROC glad_eglReleaseTexImage;
|
||||
PFNEGLQUERYDISPLAYATTRIBEXTPROC glad_eglQueryDisplayAttribEXT;
|
||||
PFNEGLDESTROYCONTEXTPROC glad_eglDestroyContext;
|
||||
PFNEGLQUERYDEVICESTRINGEXTPROC glad_eglQueryDeviceStringEXT;
|
||||
PFNEGLCREATEWINDOWSURFACEPROC glad_eglCreateWindowSurface;
|
||||
PFNEGLGETCURRENTCONTEXTPROC glad_eglGetCurrentContext;
|
||||
PFNEGLINITIALIZEPROC glad_eglInitialize;
|
||||
PFNEGLDESTROYSURFACEPROC glad_eglDestroySurface;
|
||||
PFNEGLMAKECURRENTPROC glad_eglMakeCurrent;
|
||||
PFNEGLCREATEPLATFORMWINDOWSURFACEEXTPROC glad_eglCreatePlatformWindowSurfaceEXT;
|
||||
PFNEGLSWAPINTERVALPROC glad_eglSwapInterval;
|
||||
PFNEGLCREATESYNCPROC glad_eglCreateSync;
|
||||
PFNEGLGETSYNCATTRIBPROC glad_eglGetSyncAttrib;
|
||||
PFNEGLSURFACEATTRIBPROC glad_eglSurfaceAttrib;
|
||||
PFNEGLWAITGLPROC glad_eglWaitGL;
|
||||
PFNEGLQUERYSURFACEPROC glad_eglQuerySurface;
|
||||
PFNEGLGETCONFIGSPROC glad_eglGetConfigs;
|
||||
PFNEGLWAITCLIENTPROC glad_eglWaitClient;
|
||||
PFNEGLCREATEPBUFFERFROMCLIENTBUFFERPROC glad_eglCreatePbufferFromClientBuffer;
|
||||
|
||||
|
||||
static void load_EGL_VERSION_1_0( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_EGL_VERSION_1_0) return;
|
||||
eglCreatePbufferSurface = (PFNEGLCREATEPBUFFERSURFACEPROC) load("eglCreatePbufferSurface", userptr);
|
||||
eglGetError = (PFNEGLGETERRORPROC) load("eglGetError", userptr);
|
||||
eglGetProcAddress = (PFNEGLGETPROCADDRESSPROC) load("eglGetProcAddress", userptr);
|
||||
eglGetCurrentDisplay = (PFNEGLGETCURRENTDISPLAYPROC) load("eglGetCurrentDisplay", userptr);
|
||||
eglQueryContext = (PFNEGLQUERYCONTEXTPROC) load("eglQueryContext", userptr);
|
||||
eglSwapBuffers = (PFNEGLSWAPBUFFERSPROC) load("eglSwapBuffers", userptr);
|
||||
eglCreateContext = (PFNEGLCREATECONTEXTPROC) load("eglCreateContext", userptr);
|
||||
eglChooseConfig = (PFNEGLCHOOSECONFIGPROC) load("eglChooseConfig", userptr);
|
||||
eglWaitNative = (PFNEGLWAITNATIVEPROC) load("eglWaitNative", userptr);
|
||||
eglTerminate = (PFNEGLTERMINATEPROC) load("eglTerminate", userptr);
|
||||
eglCopyBuffers = (PFNEGLCOPYBUFFERSPROC) load("eglCopyBuffers", userptr);
|
||||
eglGetConfigAttrib = (PFNEGLGETCONFIGATTRIBPROC) load("eglGetConfigAttrib", userptr);
|
||||
eglGetCurrentSurface = (PFNEGLGETCURRENTSURFACEPROC) load("eglGetCurrentSurface", userptr);
|
||||
eglCreatePixmapSurface = (PFNEGLCREATEPIXMAPSURFACEPROC) load("eglCreatePixmapSurface", userptr);
|
||||
eglGetDisplay = (PFNEGLGETDISPLAYPROC) load("eglGetDisplay", userptr);
|
||||
eglQueryString = (PFNEGLQUERYSTRINGPROC) load("eglQueryString", userptr);
|
||||
eglDestroyContext = (PFNEGLDESTROYCONTEXTPROC) load("eglDestroyContext", userptr);
|
||||
eglCreateWindowSurface = (PFNEGLCREATEWINDOWSURFACEPROC) load("eglCreateWindowSurface", userptr);
|
||||
eglInitialize = (PFNEGLINITIALIZEPROC) load("eglInitialize", userptr);
|
||||
eglDestroySurface = (PFNEGLDESTROYSURFACEPROC) load("eglDestroySurface", userptr);
|
||||
eglMakeCurrent = (PFNEGLMAKECURRENTPROC) load("eglMakeCurrent", userptr);
|
||||
eglWaitGL = (PFNEGLWAITGLPROC) load("eglWaitGL", userptr);
|
||||
eglQuerySurface = (PFNEGLQUERYSURFACEPROC) load("eglQuerySurface", userptr);
|
||||
eglGetConfigs = (PFNEGLGETCONFIGSPROC) load("eglGetConfigs", userptr);
|
||||
}
|
||||
static void load_EGL_VERSION_1_1( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_EGL_VERSION_1_1) return;
|
||||
eglReleaseTexImage = (PFNEGLRELEASETEXIMAGEPROC) load("eglReleaseTexImage", userptr);
|
||||
eglSurfaceAttrib = (PFNEGLSURFACEATTRIBPROC) load("eglSurfaceAttrib", userptr);
|
||||
eglBindTexImage = (PFNEGLBINDTEXIMAGEPROC) load("eglBindTexImage", userptr);
|
||||
eglSwapInterval = (PFNEGLSWAPINTERVALPROC) load("eglSwapInterval", userptr);
|
||||
}
|
||||
static void load_EGL_VERSION_1_2( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_EGL_VERSION_1_2) return;
|
||||
eglBindAPI = (PFNEGLBINDAPIPROC) load("eglBindAPI", userptr);
|
||||
eglQueryAPI = (PFNEGLQUERYAPIPROC) load("eglQueryAPI", userptr);
|
||||
eglWaitClient = (PFNEGLWAITCLIENTPROC) load("eglWaitClient", userptr);
|
||||
eglCreatePbufferFromClientBuffer = (PFNEGLCREATEPBUFFERFROMCLIENTBUFFERPROC) load("eglCreatePbufferFromClientBuffer", userptr);
|
||||
eglReleaseThread = (PFNEGLRELEASETHREADPROC) load("eglReleaseThread", userptr);
|
||||
}
|
||||
static void load_EGL_VERSION_1_4( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_EGL_VERSION_1_4) return;
|
||||
eglGetCurrentContext = (PFNEGLGETCURRENTCONTEXTPROC) load("eglGetCurrentContext", userptr);
|
||||
}
|
||||
static void load_EGL_VERSION_1_5( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_EGL_VERSION_1_5) return;
|
||||
eglDestroySync = (PFNEGLDESTROYSYNCPROC) load("eglDestroySync", userptr);
|
||||
eglCreateImage = (PFNEGLCREATEIMAGEPROC) load("eglCreateImage", userptr);
|
||||
eglGetPlatformDisplay = (PFNEGLGETPLATFORMDISPLAYPROC) load("eglGetPlatformDisplay", userptr);
|
||||
eglDestroyImage = (PFNEGLDESTROYIMAGEPROC) load("eglDestroyImage", userptr);
|
||||
eglClientWaitSync = (PFNEGLCLIENTWAITSYNCPROC) load("eglClientWaitSync", userptr);
|
||||
eglWaitSync = (PFNEGLWAITSYNCPROC) load("eglWaitSync", userptr);
|
||||
eglCreateSync = (PFNEGLCREATESYNCPROC) load("eglCreateSync", userptr);
|
||||
eglGetSyncAttrib = (PFNEGLGETSYNCATTRIBPROC) load("eglGetSyncAttrib", userptr);
|
||||
eglCreatePlatformWindowSurface = (PFNEGLCREATEPLATFORMWINDOWSURFACEPROC) load("eglCreatePlatformWindowSurface", userptr);
|
||||
eglCreatePlatformPixmapSurface = (PFNEGLCREATEPLATFORMPIXMAPSURFACEPROC) load("eglCreatePlatformPixmapSurface", userptr);
|
||||
}
|
||||
static void load_EGL_EXT_platform_base( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_EGL_EXT_platform_base) return;
|
||||
eglCreatePlatformWindowSurfaceEXT = (PFNEGLCREATEPLATFORMWINDOWSURFACEEXTPROC) load("eglCreatePlatformWindowSurfaceEXT", userptr);
|
||||
eglGetPlatformDisplayEXT = (PFNEGLGETPLATFORMDISPLAYEXTPROC) load("eglGetPlatformDisplayEXT", userptr);
|
||||
eglCreatePlatformPixmapSurfaceEXT = (PFNEGLCREATEPLATFORMPIXMAPSURFACEEXTPROC) load("eglCreatePlatformPixmapSurfaceEXT", userptr);
|
||||
}
|
||||
static void load_EGL_EXT_device_enumeration( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_EGL_EXT_device_enumeration) return;
|
||||
eglQueryDevicesEXT = (PFNEGLQUERYDEVICESEXTPROC) load("eglQueryDevicesEXT", userptr);
|
||||
}
|
||||
static void load_EGL_EXT_device_query( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_EGL_EXT_device_query) return;
|
||||
eglQueryDisplayAttribEXT = (PFNEGLQUERYDISPLAYATTRIBEXTPROC) load("eglQueryDisplayAttribEXT", userptr);
|
||||
eglQueryDeviceStringEXT = (PFNEGLQUERYDEVICESTRINGEXTPROC) load("eglQueryDeviceStringEXT", userptr);
|
||||
eglQueryDeviceAttribEXT = (PFNEGLQUERYDEVICEATTRIBEXTPROC) load("eglQueryDeviceAttribEXT", userptr);
|
||||
eglQueryDisplayAttribKHR = (PFNEGLQUERYDISPLAYATTRIBKHRPROC) load("eglQueryDisplayAttribKHR", userptr);
|
||||
}
|
||||
static void load_EGL_EXT_device_base( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_EGL_EXT_device_base) return;
|
||||
eglQueryDisplayAttribEXT = (PFNEGLQUERYDISPLAYATTRIBEXTPROC) load("eglQueryDisplayAttribEXT", userptr);
|
||||
eglQueryDevicesEXT = (PFNEGLQUERYDEVICESEXTPROC) load("eglQueryDevicesEXT", userptr);
|
||||
eglQueryDeviceStringEXT = (PFNEGLQUERYDEVICESTRINGEXTPROC) load("eglQueryDeviceStringEXT", userptr);
|
||||
eglQueryDeviceAttribEXT = (PFNEGLQUERYDEVICEATTRIBEXTPROC) load("eglQueryDeviceAttribEXT", userptr);
|
||||
eglQueryDisplayAttribKHR = (PFNEGLQUERYDISPLAYATTRIBKHRPROC) load("eglQueryDisplayAttribKHR", userptr);
|
||||
}
|
||||
|
||||
|
||||
|
||||
static int get_exts(EGLDisplay display, const char **extensions) {
|
||||
*extensions = eglQueryString(display, EGL_EXTENSIONS);
|
||||
|
||||
return extensions != NULL;
|
||||
}
|
||||
|
||||
static int has_ext(const char *extensions, const char *ext) {
|
||||
const char *loc;
|
||||
const char *terminator;
|
||||
if(extensions == NULL) {
|
||||
return 0;
|
||||
}
|
||||
while(1) {
|
||||
loc = strstr(extensions, ext);
|
||||
if(loc == NULL) {
|
||||
return 0;
|
||||
}
|
||||
terminator = loc + strlen(ext);
|
||||
if((loc == extensions || *(loc - 1) == ' ') &&
|
||||
(*terminator == ' ' || *terminator == '\0')) {
|
||||
return 1;
|
||||
}
|
||||
extensions = terminator;
|
||||
}
|
||||
}
|
||||
|
||||
static GLADapiproc glad_egl_get_proc_from_userptr(const char *name, void *userptr) {
|
||||
return (GLAD_GNUC_EXTENSION (GLADapiproc (*)(const char *name)) userptr)(name);
|
||||
}
|
||||
|
||||
static int find_extensionsEGL(EGLDisplay display) {
|
||||
const char *extensions;
|
||||
if (!get_exts(display, &extensions)) return 0;
|
||||
|
||||
GLAD_EGL_EXT_platform_device = has_ext(extensions, "EGL_EXT_platform_device");
|
||||
GLAD_EGL_EXT_platform_base = has_ext(extensions, "EGL_EXT_platform_base");
|
||||
GLAD_EGL_NV_device_cuda = has_ext(extensions, "EGL_NV_device_cuda");
|
||||
GLAD_EGL_EXT_device_enumeration = has_ext(extensions, "EGL_EXT_device_enumeration");
|
||||
GLAD_EGL_EXT_device_query = has_ext(extensions, "EGL_EXT_device_query");
|
||||
GLAD_EGL_EXT_device_base = has_ext(extensions, "EGL_EXT_device_base");
|
||||
GLAD_EGL_NV_cuda_event = has_ext(extensions, "EGL_NV_cuda_event");
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int find_coreEGL(EGLDisplay display) {
|
||||
int major, minor;
|
||||
const char *version;
|
||||
|
||||
if (display == NULL) {
|
||||
display = EGL_NO_DISPLAY; /* this is usually NULL, better safe than sorry */
|
||||
}
|
||||
if (display == EGL_NO_DISPLAY) {
|
||||
display = eglGetCurrentDisplay();
|
||||
}
|
||||
if (display == EGL_NO_DISPLAY) {
|
||||
display = eglGetDisplay(EGL_DEFAULT_DISPLAY);
|
||||
}
|
||||
if (display == EGL_NO_DISPLAY) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
version = eglQueryString(display, EGL_VERSION);
|
||||
(void) eglGetError();
|
||||
|
||||
if (version == NULL) {
|
||||
major = 1;
|
||||
minor = 0;
|
||||
} else {
|
||||
GLAD_IMPL_UTIL_SSCANF(version, "%d.%d", &major, &minor);
|
||||
}
|
||||
|
||||
GLAD_EGL_VERSION_1_0 = (major == 1 && minor >= 0) || major > 1;
|
||||
GLAD_EGL_VERSION_1_1 = (major == 1 && minor >= 1) || major > 1;
|
||||
GLAD_EGL_VERSION_1_2 = (major == 1 && minor >= 2) || major > 1;
|
||||
GLAD_EGL_VERSION_1_3 = (major == 1 && minor >= 3) || major > 1;
|
||||
GLAD_EGL_VERSION_1_4 = (major == 1 && minor >= 4) || major > 1;
|
||||
GLAD_EGL_VERSION_1_5 = (major == 1 && minor >= 5) || major > 1;
|
||||
|
||||
return GLAD_MAKE_VERSION(major, minor);
|
||||
}
|
||||
|
||||
int gladLoadEGLUserPtr(EGLDisplay display, GLADuserptrloadfunc load, void* userptr) {
|
||||
int version;
|
||||
eglGetDisplay = (PFNEGLGETDISPLAYPROC) load("eglGetDisplay", userptr);
|
||||
eglGetCurrentDisplay = (PFNEGLGETCURRENTDISPLAYPROC) load("eglGetCurrentDisplay", userptr);
|
||||
eglQueryString = (PFNEGLQUERYSTRINGPROC) load("eglQueryString", userptr);
|
||||
eglGetError = (PFNEGLGETERRORPROC) load("eglGetError", userptr);
|
||||
if (eglGetDisplay == NULL || eglGetCurrentDisplay == NULL || eglQueryString == NULL || eglGetError == NULL) return 0;
|
||||
|
||||
version = find_coreEGL(display);
|
||||
if (!version) return 0;
|
||||
load_EGL_VERSION_1_0(load, userptr);
|
||||
load_EGL_VERSION_1_1(load, userptr);
|
||||
load_EGL_VERSION_1_2(load, userptr);
|
||||
load_EGL_VERSION_1_4(load, userptr);
|
||||
load_EGL_VERSION_1_5(load, userptr);
|
||||
|
||||
if (!find_extensionsEGL(display)) return 0;
|
||||
load_EGL_EXT_platform_base(load, userptr);
|
||||
load_EGL_EXT_device_enumeration(load, userptr);
|
||||
load_EGL_EXT_device_query(load, userptr);
|
||||
load_EGL_EXT_device_base(load, userptr);
|
||||
|
||||
return version;
|
||||
}
|
||||
|
||||
int gladLoadEGL(EGLDisplay display, GLADloadfunc load) {
|
||||
return gladLoadEGLUserPtr(display, glad_egl_get_proc_from_userptr, GLAD_GNUC_EXTENSION (void*) load);
|
||||
}
|
||||
|
||||
|
||||
#ifdef GLAD_EGL
|
||||
|
||||
#ifndef GLAD_LOADER_LIBRARY_C_
|
||||
#define GLAD_LOADER_LIBRARY_C_
|
||||
|
||||
#include <stddef.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#if GLAD_PLATFORM_WIN32
|
||||
#include <windows.h>
|
||||
#else
|
||||
#include <dlfcn.h>
|
||||
#endif
|
||||
|
||||
|
||||
static void* glad_get_dlopen_handle(const char *lib_names[], int length) {
|
||||
void *handle = NULL;
|
||||
int i;
|
||||
|
||||
for (i = 0; i < length; ++i) {
|
||||
#if GLAD_PLATFORM_WIN32
|
||||
#if GLAD_PLATFORM_UWP
|
||||
size_t buffer_size = (strlen(lib_names[i]) + 1) * sizeof(WCHAR);
|
||||
LPWSTR buffer = (LPWSTR) malloc(buffer_size);
|
||||
if (buffer != NULL) {
|
||||
int ret = MultiByteToWideChar(CP_ACP, 0, lib_names[i], -1, buffer, buffer_size);
|
||||
if (ret != 0) {
|
||||
handle = (void*) LoadPackagedLibrary(buffer, 0);
|
||||
}
|
||||
free((void*) buffer);
|
||||
}
|
||||
#else
|
||||
handle = (void*) LoadLibraryA(lib_names[i]);
|
||||
#endif
|
||||
#else
|
||||
handle = dlopen(lib_names[i], RTLD_LAZY | RTLD_LOCAL);
|
||||
#endif
|
||||
if (handle != NULL) {
|
||||
return handle;
|
||||
}
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static void glad_close_dlopen_handle(void* handle) {
|
||||
if (handle != NULL) {
|
||||
#if GLAD_PLATFORM_WIN32
|
||||
FreeLibrary((HMODULE) handle);
|
||||
#else
|
||||
dlclose(handle);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
static GLADapiproc glad_dlsym_handle(void* handle, const char *name) {
|
||||
if (handle == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
#if GLAD_PLATFORM_WIN32
|
||||
return (GLADapiproc) GetProcAddress((HMODULE) handle, name);
|
||||
#else
|
||||
return GLAD_GNUC_EXTENSION (GLADapiproc) dlsym(handle, name);
|
||||
#endif
|
||||
}
|
||||
|
||||
#endif /* GLAD_LOADER_LIBRARY_C_ */
|
||||
|
||||
struct _glad_egl_userptr {
|
||||
void *handle;
|
||||
PFNEGLGETPROCADDRESSPROC get_proc_address_ptr;
|
||||
};
|
||||
|
||||
static GLADapiproc glad_egl_get_proc(const char* name, void *vuserptr) {
|
||||
struct _glad_egl_userptr userptr = *(struct _glad_egl_userptr*) vuserptr;
|
||||
GLADapiproc result = NULL;
|
||||
|
||||
result = glad_dlsym_handle(userptr.handle, name);
|
||||
if (result == NULL) {
|
||||
result = GLAD_GNUC_EXTENSION (GLADapiproc) userptr.get_proc_address_ptr(name);
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
static void* _egl_handle = NULL;
|
||||
|
||||
int gladLoaderLoadEGL(EGLDisplay display) {
|
||||
#ifdef __APPLE__
|
||||
static const char *NAMES[] = {"libEGL.dylib"};
|
||||
#elif GLAD_PLATFORM_WIN32
|
||||
static const char *NAMES[] = {"libEGL.dll", "EGL.dll"};
|
||||
#else
|
||||
static const char *NAMES[] = {"libEGL.so.1", "libEGL.so"};
|
||||
#endif
|
||||
|
||||
int version = 0;
|
||||
int did_load = 0;
|
||||
struct _glad_egl_userptr userptr;
|
||||
|
||||
if (_egl_handle == NULL) {
|
||||
_egl_handle = glad_get_dlopen_handle(NAMES, sizeof(NAMES) / sizeof(NAMES[0]));
|
||||
did_load = _egl_handle != NULL;
|
||||
}
|
||||
|
||||
if (_egl_handle != NULL) {
|
||||
userptr.handle = _egl_handle;
|
||||
userptr.get_proc_address_ptr = (PFNEGLGETPROCADDRESSPROC) glad_dlsym_handle(_egl_handle, "eglGetProcAddress");
|
||||
if (userptr.get_proc_address_ptr != NULL) {
|
||||
version = gladLoadEGLUserPtr(display, glad_egl_get_proc, &userptr);
|
||||
}
|
||||
|
||||
if (!version && did_load) {
|
||||
glad_close_dlopen_handle(_egl_handle);
|
||||
_egl_handle = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
return version;
|
||||
}
|
||||
|
||||
void gladLoaderUnloadEGL() {
|
||||
if (_egl_handle != NULL) {
|
||||
glad_close_dlopen_handle(_egl_handle);
|
||||
_egl_handle = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
#endif /* GLAD_EGL */
|
File diff suppressed because it is too large
Load Diff
|
@ -1,559 +0,0 @@
|
|||
/**
|
||||
* Loader generated by glad 0.1.11a0 on Wed Jun 13 07:59:54 2018
|
||||
*
|
||||
* Generator: C/C++
|
||||
* Specification: egl
|
||||
* Extensions: 7
|
||||
*
|
||||
* APIs:
|
||||
* - egl=1.5
|
||||
*
|
||||
* Options:
|
||||
* - HEADER_ONLY = False
|
||||
* - DEBUG = False
|
||||
* - MX = False
|
||||
* - LOADER = True
|
||||
* - MX_GLOBAL = False
|
||||
* - ALIAS = False
|
||||
*
|
||||
* Commandline:
|
||||
* --api='egl=1.5' --extensions='EGL_EXT_platform_device,EGL_EXT_platform_base,EGL_NV_device_cuda,EGL_EXT_device_enumeration,EGL_EXT_device_query,EGL_EXT_device_base,EGL_NV_cuda_event' c --loader
|
||||
*
|
||||
* Online:
|
||||
* http://glad2.dav1d.de/#merge=off&api=egl%3D1.5&extensions=EGL_EXT_platform_device%2CEGL_EXT_platform_base%2CEGL_NV_device_cuda%2CEGL_EXT_device_enumeration%2CEGL_EXT_device_query%2CEGL_EXT_device_base%2CEGL_NV_cuda_event&generator=c&header_only=off&debug=off&mx=off&loader=on&mx_global=off&alias=off
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef GLAD_EGL_H_
|
||||
#define GLAD_EGL_H_
|
||||
|
||||
|
||||
#define GLAD_EGL
|
||||
#define GLAD_OPTION_EGL_LOADER
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
#ifndef GLAD_PLATFORM_H_
|
||||
#define GLAD_PLATFORM_H_
|
||||
|
||||
#if defined(_WIN32) || defined(__WIN32__) || defined(WIN32) || defined(__MINGW32__)
|
||||
#define GLAD_PLATFORM_WIN32 1
|
||||
#else
|
||||
#define GLAD_PLATFORM_WIN32 0
|
||||
#endif
|
||||
|
||||
|
||||
#ifndef GLAD_PLATFORM_UWP
|
||||
#if defined(_MSC_VER) && !defined(GLAD_INTERNAL_HAVE_WINAPIFAMILY)
|
||||
#ifdef __has_include
|
||||
#if __has_include(<winapifamily.h>)
|
||||
#define GLAD_INTERNAL_HAVE_WINAPIFAMILY 1
|
||||
#endif
|
||||
#elif _MSC_VER >= 1700 && !_USING_V110_SDK71_
|
||||
#define GLAD_INTERNAL_HAVE_WINAPIFAMILY 1
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifdef GLAD_INTERNAL_HAVE_WINAPIFAMILY
|
||||
#include <winapifamily.h>
|
||||
#if !WINAPI_FAMILY_PARTITION(WINAPI_PARTITION_DESKTOP) && WINAPI_FAMILY_PARTITION(WINAPI_PARTITION_APP)
|
||||
#define GLAD_PLATFORM_UWP 1
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifndef GLAD_PLATFORM_UWP
|
||||
#define GLAD_PLATFORM_UWP 0
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifdef __GNUC__
|
||||
#define GLAD_GNUC_EXTENSION __extension__
|
||||
#else
|
||||
#define GLAD_GNUC_EXTENSION
|
||||
#endif
|
||||
|
||||
#ifndef GLAD_API_CALL
|
||||
#if defined(GLAD_API_CALL_EXPORT)
|
||||
#if GLAD_PLATFORM_WIN32 || defined(__CYGWIN__)
|
||||
#if defined(GLAD_API_CALL_EXPORT_BUILD)
|
||||
#if defined(__GNUC__)
|
||||
#define GLAD_API_CALL __attribute__ ((dllexport)) extern
|
||||
#else
|
||||
#define GLAD_API_CALL __declspec(dllexport) extern
|
||||
#endif
|
||||
#else
|
||||
#if defined(__GNUC__)
|
||||
#define GLAD_API_CALL __attribute__ ((dllimport)) extern
|
||||
#else
|
||||
#define GLAD_API_CALL __declspec(dllimport) extern
|
||||
#endif
|
||||
#endif
|
||||
#elif defined(__GNUC__) && defined(GLAD_API_CALL_EXPORT_BUILD)
|
||||
#define GLAD_API_CALL __attribute__ ((visibility ("default"))) extern
|
||||
#else
|
||||
#define GLAD_API_CALL extern
|
||||
#endif
|
||||
#else
|
||||
#define GLAD_API_CALL extern
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifdef APIENTRY
|
||||
#define GLAD_API_PTR APIENTRY
|
||||
#elif GLAD_PLATFORM_WIN32
|
||||
#define GLAD_API_PTR __stdcall
|
||||
#else
|
||||
#define GLAD_API_PTR
|
||||
#endif
|
||||
|
||||
|
||||
#define GLAD_MAKE_VERSION(major, minor) (major * 10000 + minor)
|
||||
#define GLAD_VERSION_MAJOR(version) (version / 10000)
|
||||
#define GLAD_VERSION_MINOR(version) (version % 10000)
|
||||
|
||||
typedef void (*GLADapiproc)(void);
|
||||
|
||||
typedef GLADapiproc (*GLADloadfunc)(const char *name);
|
||||
typedef GLADapiproc (*GLADuserptrloadfunc)(const char *name, void *userptr);
|
||||
|
||||
typedef void (*GLADprecallback)(const char *name, GLADapiproc apiproc, int len_args, ...);
|
||||
typedef void (*GLADpostcallback)(void *ret, const char *name, GLADapiproc apiproc, int len_args, ...);
|
||||
|
||||
#endif /* GLAD_PLATFORM_H_ */
|
||||
|
||||
#define EGL_VERSION 0x3054
|
||||
#define EGL_CONFIG_CAVEAT 0x3027
|
||||
#define EGL_NATIVE_VISUAL_ID 0x302E
|
||||
#define EGL_CONTEXT_OPENGL_ROBUST_ACCESS 0x31B2
|
||||
#define EGL_NATIVE_RENDERABLE 0x302D
|
||||
#define EGL_BAD_SURFACE 0x300D
|
||||
#define EGL_MULTISAMPLE_RESOLVE 0x3099
|
||||
#define EGL_PIXEL_ASPECT_RATIO 0x3092
|
||||
#define EGL_BLUE_SIZE 0x3022
|
||||
#define EGL_GL_TEXTURE_CUBE_MAP_POSITIVE_Y 0x30B5
|
||||
#define EGL_CONTEXT_OPENGL_RESET_NOTIFICATION_STRATEGY 0x31BD
|
||||
#define EGL_BAD_ALLOC 0x3003
|
||||
#define EGL_SAMPLES 0x3031
|
||||
#define EGL_SYNC_TYPE 0x30F7
|
||||
#define EGL_LUMINANCE_SIZE 0x303D
|
||||
#define EGL_PBUFFER_BIT 0x0001
|
||||
#define EGL_ALPHA_FORMAT_NONPRE EGL_VG_ALPHA_FORMAT_NONPRE
|
||||
#define EGL_VG_ALPHA_FORMAT_NONPRE 0x308B
|
||||
#define EGL_CONTEXT_LOST 0x300E
|
||||
#define EGL_BUFFER_PRESERVED 0x3094
|
||||
#define EGL_GL_COLORSPACE_LINEAR EGL_COLORSPACE_LINEAR
|
||||
#define EGL_SAMPLE_BUFFERS 0x3032
|
||||
#define EGL_GL_RENDERBUFFER 0x30B9
|
||||
#define EGL_UNSIGNALED 0x30F3
|
||||
#define EGL_OPENGL_ES_API 0x30A0
|
||||
#define EGL_EXTENSIONS 0x3055
|
||||
#define EGL_GL_TEXTURE_2D 0x30B1
|
||||
#define EGL_BACK_BUFFER 0x3084
|
||||
#define EGL_SYNC_CONDITION 0x30F8
|
||||
#define EGL_BAD_NATIVE_PIXMAP 0x300A
|
||||
#define EGL_CONTEXT_OPENGL_DEBUG 0x31B0
|
||||
#define EGL_TEXTURE_2D 0x305F
|
||||
#define EGL_CONFORMANT 0x3042
|
||||
#define EGL_PIXMAP_BIT 0x0002
|
||||
#define EGL_SLOW_CONFIG 0x3050
|
||||
#define EGL_CL_EVENT_HANDLE 0x309C
|
||||
#define EGL_BAD_CURRENT_SURFACE 0x3007
|
||||
#define EGL_BIND_TO_TEXTURE_RGBA 0x303A
|
||||
#define EGL_VG_COLORSPACE_sRGB EGL_COLORSPACE_sRGB
|
||||
#define EGL_IMAGE_PRESERVED 0x30D2
|
||||
#define EGL_SURFACE_TYPE 0x3033
|
||||
#define EGL_OPENVG_BIT 0x0002
|
||||
#define EGL_VERTICAL_RESOLUTION 0x3091
|
||||
#define EGL_MAX_PBUFFER_PIXELS 0x302B
|
||||
#define EGL_DEVICE_EXT 0x322C
|
||||
#define EGL_SWAP_BEHAVIOR 0x3093
|
||||
#define EGL_MULTISAMPLE_RESOLVE_BOX_BIT 0x0200
|
||||
#define EGL_VG_ALPHA_FORMAT 0x3088
|
||||
#define EGL_RENDER_BUFFER 0x3086
|
||||
#define EGL_VG_COLORSPACE 0x3087
|
||||
#define EGL_NO_CONTEXT EGL_CAST(EGLContext,0)
|
||||
#define EGL_OPENGL_API 0x30A2
|
||||
#define EGL_GL_TEXTURE_CUBE_MAP_POSITIVE_Z 0x30B7
|
||||
#define EGL_LUMINANCE_BUFFER 0x308F
|
||||
#define EGL_NO_RESET_NOTIFICATION 0x31BE
|
||||
#define EGL_COLORSPACE_sRGB 0x3089
|
||||
#define EGL_OPENGL_ES_BIT 0x0001
|
||||
#define EGL_BAD_ACCESS 0x3002
|
||||
#define EGL_OPENGL_ES2_BIT 0x0004
|
||||
#define EGL_LOSE_CONTEXT_ON_RESET 0x31BF
|
||||
#define EGL_NO_DISPLAY EGL_CAST(EGLDisplay,0)
|
||||
#define EGL_NO_DEVICE_EXT EGL_CAST(EGLDeviceEXT,0)
|
||||
#define EGL_BAD_CONFIG 0x3005
|
||||
#define EGL_NO_TEXTURE 0x305C
|
||||
#define EGL_LARGEST_PBUFFER 0x3058
|
||||
#define EGL_SWAP_BEHAVIOR_PRESERVED_BIT 0x0400
|
||||
#define EGL_ALPHA_FORMAT EGL_VG_ALPHA_FORMAT
|
||||
#define EGL_ALPHA_MASK_SIZE 0x303E
|
||||
#define EGL_GL_TEXTURE_CUBE_MAP_NEGATIVE_X 0x30B4
|
||||
#define EGL_CUDA_DEVICE_NV 0x323A
|
||||
#define EGL_VENDOR 0x3053
|
||||
#define EGL_STENCIL_SIZE 0x3026
|
||||
#define EGL_BAD_ATTRIBUTE 0x3004
|
||||
#define EGL_DRAW 0x3059
|
||||
#define EGL_SYNC_FLUSH_COMMANDS_BIT 0x0001
|
||||
#define EGL_COLORSPACE EGL_VG_COLORSPACE
|
||||
#define EGL_SYNC_CUDA_EVENT_NV 0x323C
|
||||
#define EGL_OPENVG_IMAGE 0x3096
|
||||
#define EGL_NO_IMAGE EGL_CAST(EGLImage,0)
|
||||
#define EGL_TEXTURE_TARGET 0x3081
|
||||
#define EGL_CORE_NATIVE_ENGINE 0x305B
|
||||
#define EGL_DEFAULT_DISPLAY EGL_CAST(EGLNativeDisplayType,0)
|
||||
#define EGL_SIGNALED 0x30F2
|
||||
#define EGL_GL_COLORSPACE 0x309D
|
||||
#define EGL_SYNC_PRIOR_COMMANDS_COMPLETE 0x30F0
|
||||
#define EGL_WIDTH 0x3057
|
||||
#define EGL_TRANSPARENT_RGB 0x3052
|
||||
#define EGL_SYNC_FENCE 0x30F9
|
||||
#define EGL_RENDERABLE_TYPE 0x3040
|
||||
#define EGL_TRANSPARENT_BLUE_VALUE 0x3035
|
||||
#define EGL_MAX_SWAP_INTERVAL 0x303C
|
||||
#define EGL_HEIGHT 0x3056
|
||||
#define EGL_TRANSPARENT_TYPE 0x3034
|
||||
#define EGL_DEPTH_SIZE 0x3025
|
||||
#define EGL_CONTEXT_OPENGL_PROFILE_MASK 0x30FD
|
||||
#define EGL_FOREVER 0xFFFFFFFFFFFFFFFF
|
||||
#define EGL_NATIVE_VISUAL_TYPE 0x302F
|
||||
#define EGL_GREEN_SIZE 0x3023
|
||||
#define EGL_DISPLAY_SCALING 10000
|
||||
#define EGL_WINDOW_BIT 0x0004
|
||||
#define EGL_BIND_TO_TEXTURE_RGB 0x3039
|
||||
#define EGL_VG_COLORSPACE_LINEAR EGL_COLORSPACE_LINEAR
|
||||
#define EGL_CONTEXT_OPENGL_CORE_PROFILE_BIT 0x00000001
|
||||
#define EGL_BAD_DISPLAY 0x3008
|
||||
#define EGL_CONDITION_SATISFIED 0x30F6
|
||||
#define EGL_SYNC_CL_EVENT 0x30FE
|
||||
#define EGL_COLORSPACE_LINEAR 0x308A
|
||||
#define EGL_NONE 0x3038
|
||||
#define EGL_MATCH_NATIVE_PIXMAP 0x3041
|
||||
#define EGL_MIPMAP_LEVEL 0x3083
|
||||
#define EGL_PLATFORM_DEVICE_EXT 0x313F
|
||||
#define EGL_BAD_CONTEXT 0x3006
|
||||
#define EGL_MIN_SWAP_INTERVAL 0x303B
|
||||
#define EGL_BAD_DEVICE_EXT 0x322B
|
||||
#define EGL_FALSE 0
|
||||
#define EGL_TEXTURE_FORMAT 0x3080
|
||||
#define EGL_GL_TEXTURE_3D 0x30B2
|
||||
#define EGL_COLOR_BUFFER_TYPE 0x303F
|
||||
#define EGL_MAX_PBUFFER_WIDTH 0x302C
|
||||
#define EGL_SINGLE_BUFFER 0x3085
|
||||
#define EGL_CONTEXT_OPENGL_COMPATIBILITY_PROFILE_BIT 0x00000002
|
||||
#define EGL_ALPHA_SIZE 0x3021
|
||||
#define EGL_MULTISAMPLE_RESOLVE_DEFAULT 0x309A
|
||||
#define EGL_VG_COLORSPACE_LINEAR_BIT 0x0020
|
||||
#define EGL_SYNC_STATUS 0x30F1
|
||||
#define EGL_TRUE 1
|
||||
#define EGL_TIMEOUT_EXPIRED 0x30F5
|
||||
#define EGL_NO_SURFACE EGL_CAST(EGLSurface,0)
|
||||
#define EGL_RED_SIZE 0x3024
|
||||
#define EGL_TEXTURE_RGBA 0x305E
|
||||
#define EGL_TRANSPARENT_GREEN_VALUE 0x3036
|
||||
#define EGL_GL_TEXTURE_ZOFFSET 0x30BD
|
||||
#define EGL_ALPHA_FORMAT_PRE EGL_VG_ALPHA_FORMAT_PRE
|
||||
#define EGL_UNKNOWN EGL_CAST(EGLint,-1)
|
||||
#define EGL_SUCCESS 0x3000
|
||||
#define EGL_CONTEXT_CLIENT_VERSION 0x3098
|
||||
#define EGL_GL_TEXTURE_CUBE_MAP_POSITIVE_X 0x30B3
|
||||
#define EGL_SYNC_CUDA_EVENT_COMPLETE_NV 0x323D
|
||||
#define EGL_BUFFER_SIZE 0x3020
|
||||
#define EGL_MAX_PBUFFER_HEIGHT 0x302A
|
||||
#define EGL_HORIZONTAL_RESOLUTION 0x3090
|
||||
#define EGL_SYNC_CL_EVENT_COMPLETE 0x30FF
|
||||
#define EGL_LEVEL 0x3029
|
||||
#define EGL_CONTEXT_MAJOR_VERSION EGL_CONTEXT_CLIENT_VERSION
|
||||
#define EGL_VG_ALPHA_FORMAT_PRE_BIT 0x0040
|
||||
#define EGL_GL_TEXTURE_CUBE_MAP_NEGATIVE_Z 0x30B8
|
||||
#define EGL_READ 0x305A
|
||||
#define EGL_BAD_PARAMETER 0x300C
|
||||
#define EGL_RGB_BUFFER 0x308E
|
||||
#define EGL_MULTISAMPLE_RESOLVE_BOX 0x309B
|
||||
#define EGL_NON_CONFORMANT_CONFIG 0x3051
|
||||
#define EGL_MIPMAP_TEXTURE 0x3082
|
||||
#define EGL_CONFIG_ID 0x3028
|
||||
#define EGL_CONTEXT_MINOR_VERSION 0x30FB
|
||||
#define EGL_TRANSPARENT_RED_VALUE 0x3037
|
||||
#define EGL_BUFFER_DESTROYED 0x3095
|
||||
#define EGL_CONTEXT_CLIENT_TYPE 0x3097
|
||||
#define EGL_BAD_NATIVE_WINDOW 0x300B
|
||||
#define EGL_OPENGL_BIT 0x0008
|
||||
#define EGL_OPENVG_API 0x30A1
|
||||
#define EGL_OPENGL_ES3_BIT 0x00000040
|
||||
#define EGL_BAD_MATCH 0x3009
|
||||
#define EGL_CONTEXT_OPENGL_FORWARD_COMPATIBLE 0x31B1
|
||||
#define EGL_TEXTURE_RGB 0x305D
|
||||
#define EGL_CLIENT_APIS 0x308D
|
||||
#define EGL_GL_TEXTURE_LEVEL 0x30BC
|
||||
#define EGL_NOT_INITIALIZED 0x3001
|
||||
#define EGL_NO_SYNC EGL_CAST(EGLSync,0)
|
||||
#define EGL_VG_ALPHA_FORMAT_PRE 0x308C
|
||||
#define EGL_DONT_CARE EGL_CAST(EGLint,-1)
|
||||
#define EGL_GL_TEXTURE_CUBE_MAP_NEGATIVE_Y 0x30B6
|
||||
#define EGL_GL_COLORSPACE_SRGB EGL_COLORSPACE_sRGB
|
||||
#define EGL_CUDA_EVENT_HANDLE_NV 0x323B
|
||||
|
||||
|
||||
#include <KHR/khrplatform.h>
|
||||
#include <EGL/eglplatform.h>
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
struct AHardwareBuffer;
|
||||
|
||||
typedef unsigned int EGLBoolean;
|
||||
typedef unsigned int EGLenum;
|
||||
typedef intptr_t EGLAttribKHR;
|
||||
typedef intptr_t EGLAttrib;
|
||||
typedef void *EGLClientBuffer;
|
||||
typedef void *EGLConfig;
|
||||
typedef void *EGLContext;
|
||||
typedef void *EGLDeviceEXT;
|
||||
typedef void *EGLDisplay;
|
||||
typedef void *EGLImage;
|
||||
typedef void *EGLImageKHR;
|
||||
typedef void *EGLLabelKHR;
|
||||
typedef void *EGLObjectKHR;
|
||||
typedef void *EGLOutputLayerEXT;
|
||||
typedef void *EGLOutputPortEXT;
|
||||
typedef void *EGLStreamKHR;
|
||||
typedef void *EGLSurface;
|
||||
typedef void *EGLSync;
|
||||
typedef void *EGLSyncKHR;
|
||||
typedef void *EGLSyncNV;
|
||||
typedef void (*__eglMustCastToProperFunctionPointerType)(void);
|
||||
typedef khronos_utime_nanoseconds_t EGLTimeKHR;
|
||||
typedef khronos_utime_nanoseconds_t EGLTime;
|
||||
typedef khronos_utime_nanoseconds_t EGLTimeNV;
|
||||
typedef khronos_utime_nanoseconds_t EGLuint64NV;
|
||||
typedef khronos_uint64_t EGLuint64KHR;
|
||||
typedef khronos_stime_nanoseconds_t EGLnsecsANDROID;
|
||||
typedef int EGLNativeFileDescriptorKHR;
|
||||
typedef khronos_ssize_t EGLsizeiANDROID;
|
||||
typedef void (*EGLSetBlobFuncANDROID) (const void *key, EGLsizeiANDROID keySize, const void *value, EGLsizeiANDROID valueSize);
|
||||
typedef EGLsizeiANDROID (*EGLGetBlobFuncANDROID) (const void *key, EGLsizeiANDROID keySize, void *value, EGLsizeiANDROID valueSize);
|
||||
struct EGLClientPixmapHI {
|
||||
void *pData;
|
||||
EGLint iWidth;
|
||||
EGLint iHeight;
|
||||
EGLint iStride;
|
||||
};
|
||||
typedef void (GLAD_API_PTR *EGLDEBUGPROCKHR)(EGLenum error,const char *command,EGLint messageType,EGLLabelKHR threadLabel,EGLLabelKHR objectLabel,const char* message);
|
||||
|
||||
|
||||
#define EGL_VERSION_1_0 1
|
||||
GLAD_API_CALL int GLAD_EGL_VERSION_1_0;
|
||||
#define EGL_VERSION_1_1 1
|
||||
GLAD_API_CALL int GLAD_EGL_VERSION_1_1;
|
||||
#define EGL_VERSION_1_2 1
|
||||
GLAD_API_CALL int GLAD_EGL_VERSION_1_2;
|
||||
#define EGL_VERSION_1_3 1
|
||||
GLAD_API_CALL int GLAD_EGL_VERSION_1_3;
|
||||
#define EGL_VERSION_1_4 1
|
||||
GLAD_API_CALL int GLAD_EGL_VERSION_1_4;
|
||||
#define EGL_VERSION_1_5 1
|
||||
GLAD_API_CALL int GLAD_EGL_VERSION_1_5;
|
||||
#define EGL_EXT_platform_device 1
|
||||
GLAD_API_CALL int GLAD_EGL_EXT_platform_device;
|
||||
#define EGL_EXT_platform_base 1
|
||||
GLAD_API_CALL int GLAD_EGL_EXT_platform_base;
|
||||
#define EGL_NV_device_cuda 1
|
||||
GLAD_API_CALL int GLAD_EGL_NV_device_cuda;
|
||||
#define EGL_EXT_device_enumeration 1
|
||||
GLAD_API_CALL int GLAD_EGL_EXT_device_enumeration;
|
||||
#define EGL_EXT_device_query 1
|
||||
GLAD_API_CALL int GLAD_EGL_EXT_device_query;
|
||||
#define EGL_EXT_device_base 1
|
||||
GLAD_API_CALL int GLAD_EGL_EXT_device_base;
|
||||
#define EGL_NV_cuda_event 1
|
||||
GLAD_API_CALL int GLAD_EGL_NV_cuda_event;
|
||||
|
||||
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLQUERYDEVICESEXTPROC)(EGLint max_devices, EGLDeviceEXT * devices, EGLint * num_devices);
|
||||
typedef EGLSurface (GLAD_API_PTR *PFNEGLCREATEPBUFFERSURFACEPROC)(EGLDisplay dpy, EGLConfig config, const EGLint * attrib_list);
|
||||
typedef EGLint (GLAD_API_PTR *PFNEGLGETERRORPROC)(void);
|
||||
typedef __eglMustCastToProperFunctionPointerType (GLAD_API_PTR *PFNEGLGETPROCADDRESSPROC)(const char * procname);
|
||||
typedef EGLDisplay (GLAD_API_PTR *PFNEGLGETCURRENTDISPLAYPROC)(void);
|
||||
typedef EGLenum (GLAD_API_PTR *PFNEGLQUERYAPIPROC)(void);
|
||||
typedef EGLSurface (GLAD_API_PTR *PFNEGLCREATEPLATFORMPIXMAPSURFACEPROC)(EGLDisplay dpy, EGLConfig config, void * native_pixmap, const EGLAttrib * attrib_list);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLQUERYDISPLAYATTRIBKHRPROC)(EGLDisplay dpy, EGLint name, EGLAttrib * value);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLDESTROYSYNCPROC)(EGLDisplay dpy, EGLSync sync);
|
||||
typedef EGLImage (GLAD_API_PTR *PFNEGLCREATEIMAGEPROC)(EGLDisplay dpy, EGLContext ctx, EGLenum target, EGLClientBuffer buffer, const EGLAttrib * attrib_list);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLQUERYCONTEXTPROC)(EGLDisplay dpy, EGLContext ctx, EGLint attribute, EGLint * value);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLSWAPBUFFERSPROC)(EGLDisplay dpy, EGLSurface surface);
|
||||
typedef EGLContext (GLAD_API_PTR *PFNEGLCREATECONTEXTPROC)(EGLDisplay dpy, EGLConfig config, EGLContext share_context, const EGLint * attrib_list);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLCHOOSECONFIGPROC)(EGLDisplay dpy, const EGLint * attrib_list, EGLConfig * configs, EGLint config_size, EGLint * num_config);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLBINDAPIPROC)(EGLenum api);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLWAITNATIVEPROC)(EGLint engine);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLTERMINATEPROC)(EGLDisplay dpy);
|
||||
typedef EGLSurface (GLAD_API_PTR *PFNEGLCREATEPLATFORMPIXMAPSURFACEEXTPROC)(EGLDisplay dpy, EGLConfig config, void * native_pixmap, const EGLint * attrib_list);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLRELEASETHREADPROC)(void);
|
||||
typedef EGLSurface (GLAD_API_PTR *PFNEGLCREATEPLATFORMWINDOWSURFACEPROC)(EGLDisplay dpy, EGLConfig config, void * native_window, const EGLAttrib * attrib_list);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLGETCONFIGATTRIBPROC)(EGLDisplay dpy, EGLConfig config, EGLint attribute, EGLint * value);
|
||||
typedef EGLSurface (GLAD_API_PTR *PFNEGLGETCURRENTSURFACEPROC)(EGLint readdraw);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLCOPYBUFFERSPROC)(EGLDisplay dpy, EGLSurface surface, EGLNativePixmapType target);
|
||||
typedef EGLDisplay (GLAD_API_PTR *PFNEGLGETPLATFORMDISPLAYEXTPROC)(EGLenum platform, void * native_display, const EGLint * attrib_list);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLQUERYDEVICEATTRIBEXTPROC)(EGLDeviceEXT device, EGLint attribute, EGLAttrib * value);
|
||||
typedef EGLSurface (GLAD_API_PTR *PFNEGLCREATEPIXMAPSURFACEPROC)(EGLDisplay dpy, EGLConfig config, EGLNativePixmapType pixmap, const EGLint * attrib_list);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLBINDTEXIMAGEPROC)(EGLDisplay dpy, EGLSurface surface, EGLint buffer);
|
||||
typedef EGLDisplay (GLAD_API_PTR *PFNEGLGETPLATFORMDISPLAYPROC)(EGLenum platform, void * native_display, const EGLAttrib * attrib_list);
|
||||
typedef EGLDisplay (GLAD_API_PTR *PFNEGLGETDISPLAYPROC)(EGLNativeDisplayType display_id);
|
||||
typedef const char * (GLAD_API_PTR *PFNEGLQUERYSTRINGPROC)(EGLDisplay dpy, EGLint name);
|
||||
typedef EGLint (GLAD_API_PTR *PFNEGLCLIENTWAITSYNCPROC)(EGLDisplay dpy, EGLSync sync, EGLint flags, EGLTime timeout);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLWAITSYNCPROC)(EGLDisplay dpy, EGLSync sync, EGLint flags);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLDESTROYIMAGEPROC)(EGLDisplay dpy, EGLImage image);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLRELEASETEXIMAGEPROC)(EGLDisplay dpy, EGLSurface surface, EGLint buffer);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLQUERYDISPLAYATTRIBEXTPROC)(EGLDisplay dpy, EGLint attribute, EGLAttrib * value);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLDESTROYCONTEXTPROC)(EGLDisplay dpy, EGLContext ctx);
|
||||
typedef const char * (GLAD_API_PTR *PFNEGLQUERYDEVICESTRINGEXTPROC)(EGLDeviceEXT device, EGLint name);
|
||||
typedef EGLSurface (GLAD_API_PTR *PFNEGLCREATEWINDOWSURFACEPROC)(EGLDisplay dpy, EGLConfig config, EGLNativeWindowType win, const EGLint * attrib_list);
|
||||
typedef EGLContext (GLAD_API_PTR *PFNEGLGETCURRENTCONTEXTPROC)(void);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLINITIALIZEPROC)(EGLDisplay dpy, EGLint * major, EGLint * minor);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLDESTROYSURFACEPROC)(EGLDisplay dpy, EGLSurface surface);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLMAKECURRENTPROC)(EGLDisplay dpy, EGLSurface draw, EGLSurface read, EGLContext ctx);
|
||||
typedef EGLSurface (GLAD_API_PTR *PFNEGLCREATEPLATFORMWINDOWSURFACEEXTPROC)(EGLDisplay dpy, EGLConfig config, void * native_window, const EGLint * attrib_list);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLSWAPINTERVALPROC)(EGLDisplay dpy, EGLint interval);
|
||||
typedef EGLSync (GLAD_API_PTR *PFNEGLCREATESYNCPROC)(EGLDisplay dpy, EGLenum type, const EGLAttrib * attrib_list);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLGETSYNCATTRIBPROC)(EGLDisplay dpy, EGLSync sync, EGLint attribute, EGLAttrib * value);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLSURFACEATTRIBPROC)(EGLDisplay dpy, EGLSurface surface, EGLint attribute, EGLint value);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLWAITGLPROC)(void);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLQUERYSURFACEPROC)(EGLDisplay dpy, EGLSurface surface, EGLint attribute, EGLint * value);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLGETCONFIGSPROC)(EGLDisplay dpy, EGLConfig * configs, EGLint config_size, EGLint * num_config);
|
||||
typedef EGLBoolean (GLAD_API_PTR *PFNEGLWAITCLIENTPROC)(void);
|
||||
typedef EGLSurface (GLAD_API_PTR *PFNEGLCREATEPBUFFERFROMCLIENTBUFFERPROC)(EGLDisplay dpy, EGLenum buftype, EGLClientBuffer buffer, EGLConfig config, const EGLint * attrib_list);
|
||||
|
||||
GLAD_API_CALL PFNEGLQUERYDEVICESEXTPROC glad_eglQueryDevicesEXT;
|
||||
#define eglQueryDevicesEXT glad_eglQueryDevicesEXT
|
||||
GLAD_API_CALL PFNEGLCREATEPBUFFERSURFACEPROC glad_eglCreatePbufferSurface;
|
||||
#define eglCreatePbufferSurface glad_eglCreatePbufferSurface
|
||||
GLAD_API_CALL PFNEGLGETERRORPROC glad_eglGetError;
|
||||
#define eglGetError glad_eglGetError
|
||||
GLAD_API_CALL PFNEGLGETPROCADDRESSPROC glad_eglGetProcAddress;
|
||||
#define eglGetProcAddress glad_eglGetProcAddress
|
||||
GLAD_API_CALL PFNEGLGETCURRENTDISPLAYPROC glad_eglGetCurrentDisplay;
|
||||
#define eglGetCurrentDisplay glad_eglGetCurrentDisplay
|
||||
GLAD_API_CALL PFNEGLQUERYAPIPROC glad_eglQueryAPI;
|
||||
#define eglQueryAPI glad_eglQueryAPI
|
||||
GLAD_API_CALL PFNEGLCREATEPLATFORMPIXMAPSURFACEPROC glad_eglCreatePlatformPixmapSurface;
|
||||
#define eglCreatePlatformPixmapSurface glad_eglCreatePlatformPixmapSurface
|
||||
GLAD_API_CALL PFNEGLQUERYDISPLAYATTRIBKHRPROC glad_eglQueryDisplayAttribKHR;
|
||||
#define eglQueryDisplayAttribKHR glad_eglQueryDisplayAttribKHR
|
||||
GLAD_API_CALL PFNEGLDESTROYSYNCPROC glad_eglDestroySync;
|
||||
#define eglDestroySync glad_eglDestroySync
|
||||
GLAD_API_CALL PFNEGLCREATEIMAGEPROC glad_eglCreateImage;
|
||||
#define eglCreateImage glad_eglCreateImage
|
||||
GLAD_API_CALL PFNEGLQUERYCONTEXTPROC glad_eglQueryContext;
|
||||
#define eglQueryContext glad_eglQueryContext
|
||||
GLAD_API_CALL PFNEGLSWAPBUFFERSPROC glad_eglSwapBuffers;
|
||||
#define eglSwapBuffers glad_eglSwapBuffers
|
||||
GLAD_API_CALL PFNEGLCREATECONTEXTPROC glad_eglCreateContext;
|
||||
#define eglCreateContext glad_eglCreateContext
|
||||
GLAD_API_CALL PFNEGLCHOOSECONFIGPROC glad_eglChooseConfig;
|
||||
#define eglChooseConfig glad_eglChooseConfig
|
||||
GLAD_API_CALL PFNEGLBINDAPIPROC glad_eglBindAPI;
|
||||
#define eglBindAPI glad_eglBindAPI
|
||||
GLAD_API_CALL PFNEGLWAITNATIVEPROC glad_eglWaitNative;
|
||||
#define eglWaitNative glad_eglWaitNative
|
||||
GLAD_API_CALL PFNEGLTERMINATEPROC glad_eglTerminate;
|
||||
#define eglTerminate glad_eglTerminate
|
||||
GLAD_API_CALL PFNEGLCREATEPLATFORMPIXMAPSURFACEEXTPROC glad_eglCreatePlatformPixmapSurfaceEXT;
|
||||
#define eglCreatePlatformPixmapSurfaceEXT glad_eglCreatePlatformPixmapSurfaceEXT
|
||||
GLAD_API_CALL PFNEGLRELEASETHREADPROC glad_eglReleaseThread;
|
||||
#define eglReleaseThread glad_eglReleaseThread
|
||||
GLAD_API_CALL PFNEGLCREATEPLATFORMWINDOWSURFACEPROC glad_eglCreatePlatformWindowSurface;
|
||||
#define eglCreatePlatformWindowSurface glad_eglCreatePlatformWindowSurface
|
||||
GLAD_API_CALL PFNEGLGETCONFIGATTRIBPROC glad_eglGetConfigAttrib;
|
||||
#define eglGetConfigAttrib glad_eglGetConfigAttrib
|
||||
GLAD_API_CALL PFNEGLGETCURRENTSURFACEPROC glad_eglGetCurrentSurface;
|
||||
#define eglGetCurrentSurface glad_eglGetCurrentSurface
|
||||
GLAD_API_CALL PFNEGLCOPYBUFFERSPROC glad_eglCopyBuffers;
|
||||
#define eglCopyBuffers glad_eglCopyBuffers
|
||||
GLAD_API_CALL PFNEGLGETPLATFORMDISPLAYEXTPROC glad_eglGetPlatformDisplayEXT;
|
||||
#define eglGetPlatformDisplayEXT glad_eglGetPlatformDisplayEXT
|
||||
GLAD_API_CALL PFNEGLQUERYDEVICEATTRIBEXTPROC glad_eglQueryDeviceAttribEXT;
|
||||
#define eglQueryDeviceAttribEXT glad_eglQueryDeviceAttribEXT
|
||||
GLAD_API_CALL PFNEGLCREATEPIXMAPSURFACEPROC glad_eglCreatePixmapSurface;
|
||||
#define eglCreatePixmapSurface glad_eglCreatePixmapSurface
|
||||
GLAD_API_CALL PFNEGLBINDTEXIMAGEPROC glad_eglBindTexImage;
|
||||
#define eglBindTexImage glad_eglBindTexImage
|
||||
GLAD_API_CALL PFNEGLGETPLATFORMDISPLAYPROC glad_eglGetPlatformDisplay;
|
||||
#define eglGetPlatformDisplay glad_eglGetPlatformDisplay
|
||||
GLAD_API_CALL PFNEGLGETDISPLAYPROC glad_eglGetDisplay;
|
||||
#define eglGetDisplay glad_eglGetDisplay
|
||||
GLAD_API_CALL PFNEGLQUERYSTRINGPROC glad_eglQueryString;
|
||||
#define eglQueryString glad_eglQueryString
|
||||
GLAD_API_CALL PFNEGLCLIENTWAITSYNCPROC glad_eglClientWaitSync;
|
||||
#define eglClientWaitSync glad_eglClientWaitSync
|
||||
GLAD_API_CALL PFNEGLWAITSYNCPROC glad_eglWaitSync;
|
||||
#define eglWaitSync glad_eglWaitSync
|
||||
GLAD_API_CALL PFNEGLDESTROYIMAGEPROC glad_eglDestroyImage;
|
||||
#define eglDestroyImage glad_eglDestroyImage
|
||||
GLAD_API_CALL PFNEGLRELEASETEXIMAGEPROC glad_eglReleaseTexImage;
|
||||
#define eglReleaseTexImage glad_eglReleaseTexImage
|
||||
GLAD_API_CALL PFNEGLQUERYDISPLAYATTRIBEXTPROC glad_eglQueryDisplayAttribEXT;
|
||||
#define eglQueryDisplayAttribEXT glad_eglQueryDisplayAttribEXT
|
||||
GLAD_API_CALL PFNEGLDESTROYCONTEXTPROC glad_eglDestroyContext;
|
||||
#define eglDestroyContext glad_eglDestroyContext
|
||||
GLAD_API_CALL PFNEGLQUERYDEVICESTRINGEXTPROC glad_eglQueryDeviceStringEXT;
|
||||
#define eglQueryDeviceStringEXT glad_eglQueryDeviceStringEXT
|
||||
GLAD_API_CALL PFNEGLCREATEWINDOWSURFACEPROC glad_eglCreateWindowSurface;
|
||||
#define eglCreateWindowSurface glad_eglCreateWindowSurface
|
||||
GLAD_API_CALL PFNEGLGETCURRENTCONTEXTPROC glad_eglGetCurrentContext;
|
||||
#define eglGetCurrentContext glad_eglGetCurrentContext
|
||||
GLAD_API_CALL PFNEGLINITIALIZEPROC glad_eglInitialize;
|
||||
#define eglInitialize glad_eglInitialize
|
||||
GLAD_API_CALL PFNEGLDESTROYSURFACEPROC glad_eglDestroySurface;
|
||||
#define eglDestroySurface glad_eglDestroySurface
|
||||
GLAD_API_CALL PFNEGLMAKECURRENTPROC glad_eglMakeCurrent;
|
||||
#define eglMakeCurrent glad_eglMakeCurrent
|
||||
GLAD_API_CALL PFNEGLCREATEPLATFORMWINDOWSURFACEEXTPROC glad_eglCreatePlatformWindowSurfaceEXT;
|
||||
#define eglCreatePlatformWindowSurfaceEXT glad_eglCreatePlatformWindowSurfaceEXT
|
||||
GLAD_API_CALL PFNEGLSWAPINTERVALPROC glad_eglSwapInterval;
|
||||
#define eglSwapInterval glad_eglSwapInterval
|
||||
GLAD_API_CALL PFNEGLCREATESYNCPROC glad_eglCreateSync;
|
||||
#define eglCreateSync glad_eglCreateSync
|
||||
GLAD_API_CALL PFNEGLGETSYNCATTRIBPROC glad_eglGetSyncAttrib;
|
||||
#define eglGetSyncAttrib glad_eglGetSyncAttrib
|
||||
GLAD_API_CALL PFNEGLSURFACEATTRIBPROC glad_eglSurfaceAttrib;
|
||||
#define eglSurfaceAttrib glad_eglSurfaceAttrib
|
||||
GLAD_API_CALL PFNEGLWAITGLPROC glad_eglWaitGL;
|
||||
#define eglWaitGL glad_eglWaitGL
|
||||
GLAD_API_CALL PFNEGLQUERYSURFACEPROC glad_eglQuerySurface;
|
||||
#define eglQuerySurface glad_eglQuerySurface
|
||||
GLAD_API_CALL PFNEGLGETCONFIGSPROC glad_eglGetConfigs;
|
||||
#define eglGetConfigs glad_eglGetConfigs
|
||||
GLAD_API_CALL PFNEGLWAITCLIENTPROC glad_eglWaitClient;
|
||||
#define eglWaitClient glad_eglWaitClient
|
||||
GLAD_API_CALL PFNEGLCREATEPBUFFERFROMCLIENTBUFFERPROC glad_eglCreatePbufferFromClientBuffer;
|
||||
#define eglCreatePbufferFromClientBuffer glad_eglCreatePbufferFromClientBuffer
|
||||
|
||||
|
||||
GLAD_API_CALL int gladLoadEGLUserPtr(EGLDisplay display, GLADuserptrloadfunc load, void *userptr);
|
||||
GLAD_API_CALL int gladLoadEGL(EGLDisplay display, GLADloadfunc load);
|
||||
|
||||
|
||||
|
||||
|
||||
#ifdef GLAD_EGL
|
||||
|
||||
GLAD_API_CALL int gladLoaderLoadEGL(EGLDisplay display);
|
||||
|
||||
GLAD_API_CALL void gladLoaderUnloadEGL(void);
|
||||
|
||||
#endif
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
#endif
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
|
@ -1,802 +0,0 @@
|
|||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <glad/glx.h>
|
||||
#ifdef DYNAMIC_LOAD_X11_FUNCTIONS
|
||||
#include <dlfcn.h>
|
||||
#endif
|
||||
|
||||
typedef Display* (* PFNXOPENDISPLAY) (_Xconst char* a);
|
||||
typedef Screen* (* PFNXDEFAULTSCREENOFDISPLAY) (Display*);
|
||||
typedef int (* PFNXSCREENNUMBEROFSCREEN) (Screen*);
|
||||
typedef struct
|
||||
{
|
||||
void* library;
|
||||
PFNXOPENDISPLAY XOpenDisplay;
|
||||
PFNXDEFAULTSCREENOFDISPLAY XDefaultScreenOfDisplay;
|
||||
PFNXSCREENNUMBEROFSCREEN XScreenNumberOfScreen;
|
||||
} X11Struct;
|
||||
#ifdef DYNAMIC_LOAD_X11_FUNCTIONS
|
||||
void initX11Struct(X11Struct *x11) {
|
||||
const char *X11_LIBRARY = "libX11.so.6";
|
||||
x11->library = dlopen(X11_LIBRARY, RTLD_LOCAL | RTLD_NOW);
|
||||
if (!x11->library) { fprintf(stderr, "Error opening X11 library %s\n", X11_LIBRARY); exit(EXIT_FAILURE); }
|
||||
int missingFunc = 0;
|
||||
missingFunc = ((x11->XOpenDisplay = (PFNXOPENDISPLAY) dlsym(x11->library,"XOpenDisplay"))==NULL) | missingFunc;
|
||||
if (missingFunc) { fprintf(stderr, "Error: missing func XOpenDisplay in %s, exiting!\n", X11_LIBRARY); exit(EXIT_FAILURE);}
|
||||
missingFunc = ((x11->XDefaultScreenOfDisplay = (PFNXDEFAULTSCREENOFDISPLAY) dlsym(x11->library,"XDefaultScreenOfDisplay"))==NULL) | missingFunc;
|
||||
if (missingFunc) { fprintf(stderr, "Error: missing func XScreenNumberOfScreen in %s, exiting!\n", X11_LIBRARY); exit(EXIT_FAILURE);}
|
||||
missingFunc = ((x11->XScreenNumberOfScreen = (PFNXSCREENNUMBEROFSCREEN) dlsym(x11->library,"XScreenNumberOfScreen"))==NULL) | missingFunc;
|
||||
if (missingFunc) { fprintf(stderr, "Error: missing func XScreenNumberOfScreen in %s, exiting!\n", X11_LIBRARY); exit(EXIT_FAILURE);}
|
||||
if (!missingFunc) { printf("X11 functions dynamically loaded using dlopen/dlsym OK!\n");}
|
||||
}
|
||||
#else
|
||||
void initX11Struct(X11Struct *x11) {
|
||||
x11->XOpenDisplay = XOpenDisplay;
|
||||
x11->XDefaultScreenOfDisplay = XDefaultScreenOfDisplay;
|
||||
x11->XScreenNumberOfScreen = XScreenNumberOfScreen;
|
||||
}
|
||||
#endif // DYNAMIC_LOAD_X11_FUNCTIONS
|
||||
|
||||
#ifndef GLAD_IMPL_UTIL_C_
|
||||
#define GLAD_IMPL_UTIL_C_
|
||||
|
||||
#if _MSC_VER >= 1400
|
||||
#define GLAD_IMPL_UTIL_STRNCPY(dest, source, len) strncpy_s(dest, len, source, len-1);
|
||||
#else
|
||||
#define GLAD_IMPL_UTIL_STRNCPY(dest, source, len) strncpy(dest, source, len);
|
||||
#endif
|
||||
|
||||
#ifdef _MSC_VER
|
||||
#define GLAD_IMPL_UTIL_SSCANF sscanf_s
|
||||
#else
|
||||
#define GLAD_IMPL_UTIL_SSCANF sscanf
|
||||
#endif
|
||||
|
||||
#endif /* GLAD_IMPL_UTIL_C_ */
|
||||
|
||||
|
||||
|
||||
|
||||
int GLAD_GLX_VERSION_1_0;
|
||||
int GLAD_GLX_VERSION_1_1;
|
||||
int GLAD_GLX_VERSION_1_2;
|
||||
int GLAD_GLX_VERSION_1_3;
|
||||
int GLAD_GLX_VERSION_1_4;
|
||||
int GLAD_GLX_MESA_copy_sub_buffer;
|
||||
int GLAD_GLX_EXT_create_context_es_profile;
|
||||
int GLAD_GLX_SGIX_pbuffer;
|
||||
int GLAD_GLX_SGI_make_current_read;
|
||||
int GLAD_GLX_OML_sync_control;
|
||||
int GLAD_GLX_SGIX_hyperpipe;
|
||||
int GLAD_GLX_INTEL_swap_event;
|
||||
int GLAD_GLX_EXT_swap_control;
|
||||
int GLAD_GLX_NV_robustness_video_memory_purge;
|
||||
int GLAD_GLX_MESA_pixmap_colormap;
|
||||
int GLAD_GLX_ARB_fbconfig_float;
|
||||
int GLAD_GLX_EXT_fbconfig_packed_float;
|
||||
int GLAD_GLX_OML_swap_method;
|
||||
int GLAD_GLX_NV_video_capture;
|
||||
int GLAD_GLX_ARB_robustness_application_isolation;
|
||||
int GLAD_GLX_ARB_create_context_robustness;
|
||||
int GLAD_GLX_EXT_visual_rating;
|
||||
int GLAD_GLX_NV_swap_group;
|
||||
int GLAD_GLX_EXT_texture_from_pixmap;
|
||||
int GLAD_GLX_SUN_get_transparent_index;
|
||||
int GLAD_GLX_MESA_release_buffers;
|
||||
int GLAD_GLX_NV_delay_before_swap;
|
||||
int GLAD_GLX_EXT_buffer_age;
|
||||
int GLAD_GLX_MESA_agp_offset;
|
||||
int GLAD_GLX_EXT_visual_info;
|
||||
int GLAD_GLX_SGI_swap_control;
|
||||
int GLAD_GLX_EXT_import_context;
|
||||
int GLAD_GLX_SGI_video_sync;
|
||||
int GLAD_GLX_3DFX_multisample;
|
||||
int GLAD_GLX_ARB_multisample;
|
||||
int GLAD_GLX_EXT_framebuffer_sRGB;
|
||||
int GLAD_GLX_SGI_cushion;
|
||||
int GLAD_GLX_ARB_robustness_share_group_isolation;
|
||||
int GLAD_GLX_SGIX_fbconfig;
|
||||
int GLAD_GLX_NV_copy_buffer;
|
||||
int GLAD_GLX_SGIX_visual_select_group;
|
||||
int GLAD_GLX_EXT_swap_control_tear;
|
||||
int GLAD_GLX_ARB_create_context;
|
||||
int GLAD_GLX_AMD_gpu_association;
|
||||
int GLAD_GLX_MESA_query_renderer;
|
||||
int GLAD_GLX_EXT_create_context_es2_profile;
|
||||
int GLAD_GLX_MESA_swap_control;
|
||||
int GLAD_GLX_SGIX_video_resize;
|
||||
int GLAD_GLX_ARB_context_flush_control;
|
||||
int GLAD_GLX_NV_video_out;
|
||||
int GLAD_GLX_EXT_no_config_context;
|
||||
int GLAD_GLX_SGIS_blended_overlay;
|
||||
int GLAD_GLX_EXT_stereo_tree;
|
||||
int GLAD_GLX_ARB_create_context_no_error;
|
||||
int GLAD_GLX_EXT_libglvnd;
|
||||
int GLAD_GLX_ARB_create_context_profile;
|
||||
int GLAD_GLX_NV_float_buffer;
|
||||
int GLAD_GLX_MESA_set_3dfx_mode;
|
||||
int GLAD_GLX_ARB_framebuffer_sRGB;
|
||||
int GLAD_GLX_ARB_get_proc_address;
|
||||
int GLAD_GLX_SGIS_shared_multisample;
|
||||
int GLAD_GLX_NV_copy_image;
|
||||
int GLAD_GLX_NV_present_video;
|
||||
int GLAD_GLX_SGIX_swap_barrier;
|
||||
int GLAD_GLX_SGIS_multisample;
|
||||
int GLAD_GLX_SGIX_swap_group;
|
||||
int GLAD_GLX_ARB_vertex_buffer_object;
|
||||
int GLAD_GLX_NV_multisample_coverage;
|
||||
|
||||
|
||||
|
||||
PFNGLXCUSHIONSGIPROC glad_glXCushionSGI;
|
||||
PFNGLXDESTROYGLXPBUFFERSGIXPROC glad_glXDestroyGLXPbufferSGIX;
|
||||
PFNGLXSENDPBUFFERTOVIDEONVPROC glad_glXSendPbufferToVideoNV;
|
||||
PFNGLXGETPROCADDRESSARBPROC glad_glXGetProcAddressARB;
|
||||
PFNGLXCREATECONTEXTATTRIBSARBPROC glad_glXCreateContextAttribsARB;
|
||||
PFNGLXJOINSWAPGROUPSGIXPROC glad_glXJoinSwapGroupSGIX;
|
||||
PFNGLXSWAPINTERVALEXTPROC glad_glXSwapIntervalEXT;
|
||||
PFNGLXQUERYHYPERPIPECONFIGSGIXPROC glad_glXQueryHyperpipeConfigSGIX;
|
||||
PFNGLXGETGPUINFOAMDPROC glad_glXGetGPUInfoAMD;
|
||||
PFNGLXGETTRANSPARENTINDEXSUNPROC glad_glXGetTransparentIndexSUN;
|
||||
PFNGLXQUERYHYPERPIPENETWORKSGIXPROC glad_glXQueryHyperpipeNetworkSGIX;
|
||||
PFNGLXQUERYGLXPBUFFERSGIXPROC glad_glXQueryGLXPbufferSGIX;
|
||||
PFNGLXCREATEGLXPIXMAPWITHCONFIGSGIXPROC glad_glXCreateGLXPixmapWithConfigSGIX;
|
||||
PFNGLXCOPYCONTEXTPROC glad_glXCopyContext;
|
||||
PFNGLXCREATEGLXPBUFFERSGIXPROC glad_glXCreateGLXPbufferSGIX;
|
||||
PFNGLXGETGPUIDSAMDPROC glad_glXGetGPUIDsAMD;
|
||||
PFNGLXDELETEASSOCIATEDCONTEXTAMDPROC glad_glXDeleteAssociatedContextAMD;
|
||||
PFNGLXGETVIDEODEVICENVPROC glad_glXGetVideoDeviceNV;
|
||||
PFNGLXWAITGLPROC glad_glXWaitGL;
|
||||
PFNGLXGETVIDEOSYNCSGIPROC glad_glXGetVideoSyncSGI;
|
||||
PFNGLXDESTROYHYPERPIPECONFIGSGIXPROC glad_glXDestroyHyperpipeConfigSGIX;
|
||||
PFNGLXHYPERPIPECONFIGSGIXPROC glad_glXHyperpipeConfigSGIX;
|
||||
PFNGLXSWAPBUFFERSMSCOMLPROC glad_glXSwapBuffersMscOML;
|
||||
PFNGLXCHOOSEFBCONFIGSGIXPROC glad_glXChooseFBConfigSGIX;
|
||||
PFNGLXWAITVIDEOSYNCSGIPROC glad_glXWaitVideoSyncSGI;
|
||||
PFNGLXWAITFORSBCOMLPROC glad_glXWaitForSbcOML;
|
||||
PFNGLXGETPROCADDRESSPROC glad_glXGetProcAddress;
|
||||
PFNGLXGETSWAPINTERVALMESAPROC glad_glXGetSwapIntervalMESA;
|
||||
PFNGLXCHANNELRECTSGIXPROC glad_glXChannelRectSGIX;
|
||||
PFNGLXWAITXPROC glad_glXWaitX;
|
||||
PFNGLXQUERYSERVERSTRINGPROC glad_glXQueryServerString;
|
||||
PFNGLXCREATEGLXPIXMAPPROC glad_glXCreateGLXPixmap;
|
||||
PFNGLXBINDSWAPBARRIERNVPROC glad_glXBindSwapBarrierNV;
|
||||
PFNGLXQUERYRENDERERSTRINGMESAPROC glad_glXQueryRendererStringMESA;
|
||||
PFNGLXRELEASEVIDEOCAPTUREDEVICENVPROC glad_glXReleaseVideoCaptureDeviceNV;
|
||||
PFNGLXWAITFORMSCOMLPROC glad_glXWaitForMscOML;
|
||||
PFNGLXCOPYSUBBUFFERMESAPROC glad_glXCopySubBufferMESA;
|
||||
PFNGLXGETCURRENTCONTEXTPROC glad_glXGetCurrentContext;
|
||||
PFNGLXSELECTEVENTPROC glad_glXSelectEvent;
|
||||
PFNGLXSWAPINTERVALSGIPROC glad_glXSwapIntervalSGI;
|
||||
PFNGLXQUERYSWAPGROUPNVPROC glad_glXQuerySwapGroupNV;
|
||||
PFNGLXMAKECURRENTREADSGIPROC glad_glXMakeCurrentReadSGI;
|
||||
PFNGLXQUERYDRAWABLEPROC glad_glXQueryDrawable;
|
||||
PFNGLXCOPYBUFFERSUBDATANVPROC glad_glXCopyBufferSubDataNV;
|
||||
PFNGLXQUERYCONTEXTPROC glad_glXQueryContext;
|
||||
PFNGLXGETCONFIGPROC glad_glXGetConfig;
|
||||
PFNGLXSET3DFXMODEMESAPROC glad_glXSet3DfxModeMESA;
|
||||
PFNGLXGETVIDEOINFONVPROC glad_glXGetVideoInfoNV;
|
||||
PFNGLXISDIRECTPROC glad_glXIsDirect;
|
||||
PFNGLXGETFBCONFIGATTRIBPROC glad_glXGetFBConfigAttrib;
|
||||
PFNGLXGETVISUALFROMFBCONFIGPROC glad_glXGetVisualFromFBConfig;
|
||||
PFNGLXBINDTEXIMAGEEXTPROC glad_glXBindTexImageEXT;
|
||||
PFNGLXBLITCONTEXTFRAMEBUFFERAMDPROC glad_glXBlitContextFramebufferAMD;
|
||||
PFNGLXQUERYVERSIONPROC glad_glXQueryVersion;
|
||||
PFNGLXSELECTEVENTSGIXPROC glad_glXSelectEventSGIX;
|
||||
PFNGLXGETMSCRATEOMLPROC glad_glXGetMscRateOML;
|
||||
PFNGLXQUERYRENDERERINTEGERMESAPROC glad_glXQueryRendererIntegerMESA;
|
||||
PFNGLXCREATEWINDOWPROC glad_glXCreateWindow;
|
||||
PFNGLXCOPYIMAGESUBDATANVPROC glad_glXCopyImageSubDataNV;
|
||||
PFNGLXSWAPINTERVALMESAPROC glad_glXSwapIntervalMESA;
|
||||
PFNGLXQUERYHYPERPIPEATTRIBSGIXPROC glad_glXQueryHyperpipeAttribSGIX;
|
||||
PFNGLXBINDVIDEOCAPTUREDEVICENVPROC glad_glXBindVideoCaptureDeviceNV;
|
||||
PFNGLXCREATECONTEXTWITHCONFIGSGIXPROC glad_glXCreateContextWithConfigSGIX;
|
||||
PFNGLXENUMERATEVIDEODEVICESNVPROC glad_glXEnumerateVideoDevicesNV;
|
||||
PFNGLXHYPERPIPEATTRIBSGIXPROC glad_glXHyperpipeAttribSGIX;
|
||||
PFNGLXDESTROYPBUFFERPROC glad_glXDestroyPbuffer;
|
||||
PFNGLXNAMEDCOPYBUFFERSUBDATANVPROC glad_glXNamedCopyBufferSubDataNV;
|
||||
PFNGLXCREATEPBUFFERPROC glad_glXCreatePbuffer;
|
||||
PFNGLXQUERYCURRENTRENDERERSTRINGMESAPROC glad_glXQueryCurrentRendererStringMESA;
|
||||
PFNGLXQUERYHYPERPIPEBESTATTRIBSGIXPROC glad_glXQueryHyperpipeBestAttribSGIX;
|
||||
PFNGLXGETFBCONFIGATTRIBSGIXPROC glad_glXGetFBConfigAttribSGIX;
|
||||
PFNGLXQUERYEXTENSIONSSTRINGPROC glad_glXQueryExtensionsString;
|
||||
PFNGLXBINDVIDEODEVICENVPROC glad_glXBindVideoDeviceNV;
|
||||
PFNGLXCREATEASSOCIATEDCONTEXTAMDPROC glad_glXCreateAssociatedContextAMD;
|
||||
PFNGLXQUERYCONTEXTINFOEXTPROC glad_glXQueryContextInfoEXT;
|
||||
PFNGLXGETSELECTEDEVENTPROC glad_glXGetSelectedEvent;
|
||||
PFNGLXGETCURRENTDISPLAYPROC glad_glXGetCurrentDisplay;
|
||||
PFNGLXDESTROYPIXMAPPROC glad_glXDestroyPixmap;
|
||||
PFNGLXGETSELECTEDEVENTSGIXPROC glad_glXGetSelectedEventSGIX;
|
||||
PFNGLXRELEASETEXIMAGEEXTPROC glad_glXReleaseTexImageEXT;
|
||||
PFNGLXUSEXFONTPROC glad_glXUseXFont;
|
||||
PFNGLXGETSYNCVALUESOMLPROC glad_glXGetSyncValuesOML;
|
||||
PFNGLXJOINSWAPGROUPNVPROC glad_glXJoinSwapGroupNV;
|
||||
PFNGLXSWAPBUFFERSPROC glad_glXSwapBuffers;
|
||||
PFNGLXDELAYBEFORESWAPNVPROC glad_glXDelayBeforeSwapNV;
|
||||
PFNGLXBINDHYPERPIPESGIXPROC glad_glXBindHyperpipeSGIX;
|
||||
PFNGLXLOCKVIDEOCAPTUREDEVICENVPROC glad_glXLockVideoCaptureDeviceNV;
|
||||
PFNGLXGETCURRENTDISPLAYEXTPROC glad_glXGetCurrentDisplayEXT;
|
||||
PFNGLXGETFBCONFIGSPROC glad_glXGetFBConfigs;
|
||||
PFNGLXGETCURRENTREADDRAWABLEPROC glad_glXGetCurrentReadDrawable;
|
||||
PFNGLXRELEASEVIDEOIMAGENVPROC glad_glXReleaseVideoImageNV;
|
||||
PFNGLXQUERYEXTENSIONPROC glad_glXQueryExtension;
|
||||
PFNGLXMAKEASSOCIATEDCONTEXTCURRENTAMDPROC glad_glXMakeAssociatedContextCurrentAMD;
|
||||
PFNGLXCHOOSEVISUALPROC glad_glXChooseVisual;
|
||||
PFNGLXDESTROYCONTEXTPROC glad_glXDestroyContext;
|
||||
PFNGLXGETCLIENTSTRINGPROC glad_glXGetClientString;
|
||||
PFNGLXDESTROYGLXPIXMAPPROC glad_glXDestroyGLXPixmap;
|
||||
PFNGLXRESETFRAMECOUNTNVPROC glad_glXResetFrameCountNV;
|
||||
PFNGLXRELEASEVIDEODEVICENVPROC glad_glXReleaseVideoDeviceNV;
|
||||
PFNGLXGETFBCONFIGFROMVISUALSGIXPROC glad_glXGetFBConfigFromVisualSGIX;
|
||||
PFNGLXCREATENEWCONTEXTPROC glad_glXCreateNewContext;
|
||||
PFNGLXMAKECONTEXTCURRENTPROC glad_glXMakeContextCurrent;
|
||||
PFNGLXQUERYMAXSWAPGROUPSNVPROC glad_glXQueryMaxSwapGroupsNV;
|
||||
PFNGLXGETVISUALFROMFBCONFIGSGIXPROC glad_glXGetVisualFromFBConfigSGIX;
|
||||
PFNGLXGETCURRENTDRAWABLEPROC glad_glXGetCurrentDrawable;
|
||||
PFNGLXGETCURRENTREADDRAWABLESGIPROC glad_glXGetCurrentReadDrawableSGI;
|
||||
PFNGLXQUERYFRAMECOUNTNVPROC glad_glXQueryFrameCountNV;
|
||||
PFNGLXGETCONTEXTGPUIDAMDPROC glad_glXGetContextGPUIDAMD;
|
||||
PFNGLXBINDSWAPBARRIERSGIXPROC glad_glXBindSwapBarrierSGIX;
|
||||
PFNGLXQUERYMAXSWAPBARRIERSSGIXPROC glad_glXQueryMaxSwapBarriersSGIX;
|
||||
PFNGLXCREATEGLXPIXMAPMESAPROC glad_glXCreateGLXPixmapMESA;
|
||||
PFNGLXMAKECURRENTPROC glad_glXMakeCurrent;
|
||||
PFNGLXDESTROYWINDOWPROC glad_glXDestroyWindow;
|
||||
PFNGLXBINDVIDEOIMAGENVPROC glad_glXBindVideoImageNV;
|
||||
PFNGLXQUERYVIDEOCAPTUREDEVICENVPROC glad_glXQueryVideoCaptureDeviceNV;
|
||||
PFNGLXQUERYCHANNELDELTASSGIXPROC glad_glXQueryChannelDeltasSGIX;
|
||||
PFNGLXENUMERATEVIDEOCAPTUREDEVICESNVPROC glad_glXEnumerateVideoCaptureDevicesNV;
|
||||
PFNGLXCREATEASSOCIATEDCONTEXTATTRIBSAMDPROC glad_glXCreateAssociatedContextAttribsAMD;
|
||||
PFNGLXGETCURRENTASSOCIATEDCONTEXTAMDPROC glad_glXGetCurrentAssociatedContextAMD;
|
||||
PFNGLXQUERYCHANNELRECTSGIXPROC glad_glXQueryChannelRectSGIX;
|
||||
PFNGLXCREATECONTEXTPROC glad_glXCreateContext;
|
||||
PFNGLXFREECONTEXTEXTPROC glad_glXFreeContextEXT;
|
||||
PFNGLXGETCONTEXTIDEXTPROC glad_glXGetContextIDEXT;
|
||||
PFNGLXQUERYCURRENTRENDERERINTEGERMESAPROC glad_glXQueryCurrentRendererIntegerMESA;
|
||||
PFNGLXCHOOSEFBCONFIGPROC glad_glXChooseFBConfig;
|
||||
PFNGLXBINDCHANNELTOWINDOWSGIXPROC glad_glXBindChannelToWindowSGIX;
|
||||
PFNGLXCHANNELRECTSYNCSGIXPROC glad_glXChannelRectSyncSGIX;
|
||||
PFNGLXIMPORTCONTEXTEXTPROC glad_glXImportContextEXT;
|
||||
PFNGLXRELEASEBUFFERSMESAPROC glad_glXReleaseBuffersMESA;
|
||||
PFNGLXCREATEPIXMAPPROC glad_glXCreatePixmap;
|
||||
PFNGLXGETAGPOFFSETMESAPROC glad_glXGetAGPOffsetMESA;
|
||||
|
||||
|
||||
static void load_GLX_VERSION_1_0( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_VERSION_1_0) return;
|
||||
glXWaitGL = (PFNGLXWAITGLPROC) load("glXWaitGL", userptr);
|
||||
glXWaitX = (PFNGLXWAITXPROC) load("glXWaitX", userptr);
|
||||
glXGetConfig = (PFNGLXGETCONFIGPROC) load("glXGetConfig", userptr);
|
||||
glXQueryVersion = (PFNGLXQUERYVERSIONPROC) load("glXQueryVersion", userptr);
|
||||
glXCreateContext = (PFNGLXCREATECONTEXTPROC) load("glXCreateContext", userptr);
|
||||
glXQueryExtension = (PFNGLXQUERYEXTENSIONPROC) load("glXQueryExtension", userptr);
|
||||
glXGetCurrentContext = (PFNGLXGETCURRENTCONTEXTPROC) load("glXGetCurrentContext", userptr);
|
||||
glXMakeCurrent = (PFNGLXMAKECURRENTPROC) load("glXMakeCurrent", userptr);
|
||||
glXCopyContext = (PFNGLXCOPYCONTEXTPROC) load("glXCopyContext", userptr);
|
||||
glXIsDirect = (PFNGLXISDIRECTPROC) load("glXIsDirect", userptr);
|
||||
glXCreateGLXPixmap = (PFNGLXCREATEGLXPIXMAPPROC) load("glXCreateGLXPixmap", userptr);
|
||||
glXGetCurrentDrawable = (PFNGLXGETCURRENTDRAWABLEPROC) load("glXGetCurrentDrawable", userptr);
|
||||
glXUseXFont = (PFNGLXUSEXFONTPROC) load("glXUseXFont", userptr);
|
||||
glXChooseVisual = (PFNGLXCHOOSEVISUALPROC) load("glXChooseVisual", userptr);
|
||||
glXDestroyContext = (PFNGLXDESTROYCONTEXTPROC) load("glXDestroyContext", userptr);
|
||||
glXDestroyGLXPixmap = (PFNGLXDESTROYGLXPIXMAPPROC) load("glXDestroyGLXPixmap", userptr);
|
||||
glXSwapBuffers = (PFNGLXSWAPBUFFERSPROC) load("glXSwapBuffers", userptr);
|
||||
}
|
||||
static void load_GLX_VERSION_1_1( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_VERSION_1_1) return;
|
||||
glXQueryServerString = (PFNGLXQUERYSERVERSTRINGPROC) load("glXQueryServerString", userptr);
|
||||
glXGetClientString = (PFNGLXGETCLIENTSTRINGPROC) load("glXGetClientString", userptr);
|
||||
glXQueryExtensionsString = (PFNGLXQUERYEXTENSIONSSTRINGPROC) load("glXQueryExtensionsString", userptr);
|
||||
}
|
||||
static void load_GLX_VERSION_1_2( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_VERSION_1_2) return;
|
||||
glXGetCurrentDisplay = (PFNGLXGETCURRENTDISPLAYPROC) load("glXGetCurrentDisplay", userptr);
|
||||
}
|
||||
static void load_GLX_VERSION_1_3( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_VERSION_1_3) return;
|
||||
glXQueryContext = (PFNGLXQUERYCONTEXTPROC) load("glXQueryContext", userptr);
|
||||
glXGetFBConfigs = (PFNGLXGETFBCONFIGSPROC) load("glXGetFBConfigs", userptr);
|
||||
glXDestroyPixmap = (PFNGLXDESTROYPIXMAPPROC) load("glXDestroyPixmap", userptr);
|
||||
glXCreateNewContext = (PFNGLXCREATENEWCONTEXTPROC) load("glXCreateNewContext", userptr);
|
||||
glXGetCurrentReadDrawable = (PFNGLXGETCURRENTREADDRAWABLEPROC) load("glXGetCurrentReadDrawable", userptr);
|
||||
glXMakeContextCurrent = (PFNGLXMAKECONTEXTCURRENTPROC) load("glXMakeContextCurrent", userptr);
|
||||
glXDestroyWindow = (PFNGLXDESTROYWINDOWPROC) load("glXDestroyWindow", userptr);
|
||||
glXChooseFBConfig = (PFNGLXCHOOSEFBCONFIGPROC) load("glXChooseFBConfig", userptr);
|
||||
glXCreatePixmap = (PFNGLXCREATEPIXMAPPROC) load("glXCreatePixmap", userptr);
|
||||
glXSelectEvent = (PFNGLXSELECTEVENTPROC) load("glXSelectEvent", userptr);
|
||||
glXGetFBConfigAttrib = (PFNGLXGETFBCONFIGATTRIBPROC) load("glXGetFBConfigAttrib", userptr);
|
||||
glXDestroyPbuffer = (PFNGLXDESTROYPBUFFERPROC) load("glXDestroyPbuffer", userptr);
|
||||
glXCreatePbuffer = (PFNGLXCREATEPBUFFERPROC) load("glXCreatePbuffer", userptr);
|
||||
glXCreateWindow = (PFNGLXCREATEWINDOWPROC) load("glXCreateWindow", userptr);
|
||||
glXGetSelectedEvent = (PFNGLXGETSELECTEDEVENTPROC) load("glXGetSelectedEvent", userptr);
|
||||
glXQueryDrawable = (PFNGLXQUERYDRAWABLEPROC) load("glXQueryDrawable", userptr);
|
||||
glXGetVisualFromFBConfig = (PFNGLXGETVISUALFROMFBCONFIGPROC) load("glXGetVisualFromFBConfig", userptr);
|
||||
}
|
||||
static void load_GLX_VERSION_1_4( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_VERSION_1_4) return;
|
||||
glXGetProcAddress = (PFNGLXGETPROCADDRESSPROC) load("glXGetProcAddress", userptr);
|
||||
}
|
||||
static void load_GLX_MESA_copy_sub_buffer( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_MESA_copy_sub_buffer) return;
|
||||
glXCopySubBufferMESA = (PFNGLXCOPYSUBBUFFERMESAPROC) load("glXCopySubBufferMESA", userptr);
|
||||
}
|
||||
static void load_GLX_SGIX_pbuffer( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_SGIX_pbuffer) return;
|
||||
glXDestroyGLXPbufferSGIX = (PFNGLXDESTROYGLXPBUFFERSGIXPROC) load("glXDestroyGLXPbufferSGIX", userptr);
|
||||
glXQueryGLXPbufferSGIX = (PFNGLXQUERYGLXPBUFFERSGIXPROC) load("glXQueryGLXPbufferSGIX", userptr);
|
||||
glXCreateGLXPbufferSGIX = (PFNGLXCREATEGLXPBUFFERSGIXPROC) load("glXCreateGLXPbufferSGIX", userptr);
|
||||
glXGetSelectedEventSGIX = (PFNGLXGETSELECTEDEVENTSGIXPROC) load("glXGetSelectedEventSGIX", userptr);
|
||||
glXSelectEventSGIX = (PFNGLXSELECTEVENTSGIXPROC) load("glXSelectEventSGIX", userptr);
|
||||
}
|
||||
static void load_GLX_SGI_make_current_read( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_SGI_make_current_read) return;
|
||||
glXGetCurrentReadDrawableSGI = (PFNGLXGETCURRENTREADDRAWABLESGIPROC) load("glXGetCurrentReadDrawableSGI", userptr);
|
||||
glXMakeCurrentReadSGI = (PFNGLXMAKECURRENTREADSGIPROC) load("glXMakeCurrentReadSGI", userptr);
|
||||
}
|
||||
static void load_GLX_OML_sync_control( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_OML_sync_control) return;
|
||||
glXWaitForMscOML = (PFNGLXWAITFORMSCOMLPROC) load("glXWaitForMscOML", userptr);
|
||||
glXGetSyncValuesOML = (PFNGLXGETSYNCVALUESOMLPROC) load("glXGetSyncValuesOML", userptr);
|
||||
glXWaitForSbcOML = (PFNGLXWAITFORSBCOMLPROC) load("glXWaitForSbcOML", userptr);
|
||||
glXSwapBuffersMscOML = (PFNGLXSWAPBUFFERSMSCOMLPROC) load("glXSwapBuffersMscOML", userptr);
|
||||
glXGetMscRateOML = (PFNGLXGETMSCRATEOMLPROC) load("glXGetMscRateOML", userptr);
|
||||
}
|
||||
static void load_GLX_SGIX_hyperpipe( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_SGIX_hyperpipe) return;
|
||||
glXQueryHyperpipeBestAttribSGIX = (PFNGLXQUERYHYPERPIPEBESTATTRIBSGIXPROC) load("glXQueryHyperpipeBestAttribSGIX", userptr);
|
||||
glXQueryHyperpipeAttribSGIX = (PFNGLXQUERYHYPERPIPEATTRIBSGIXPROC) load("glXQueryHyperpipeAttribSGIX", userptr);
|
||||
glXDestroyHyperpipeConfigSGIX = (PFNGLXDESTROYHYPERPIPECONFIGSGIXPROC) load("glXDestroyHyperpipeConfigSGIX", userptr);
|
||||
glXHyperpipeConfigSGIX = (PFNGLXHYPERPIPECONFIGSGIXPROC) load("glXHyperpipeConfigSGIX", userptr);
|
||||
glXHyperpipeAttribSGIX = (PFNGLXHYPERPIPEATTRIBSGIXPROC) load("glXHyperpipeAttribSGIX", userptr);
|
||||
glXQueryHyperpipeConfigSGIX = (PFNGLXQUERYHYPERPIPECONFIGSGIXPROC) load("glXQueryHyperpipeConfigSGIX", userptr);
|
||||
glXQueryHyperpipeNetworkSGIX = (PFNGLXQUERYHYPERPIPENETWORKSGIXPROC) load("glXQueryHyperpipeNetworkSGIX", userptr);
|
||||
glXBindHyperpipeSGIX = (PFNGLXBINDHYPERPIPESGIXPROC) load("glXBindHyperpipeSGIX", userptr);
|
||||
}
|
||||
static void load_GLX_EXT_swap_control( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_EXT_swap_control) return;
|
||||
glXSwapIntervalEXT = (PFNGLXSWAPINTERVALEXTPROC) load("glXSwapIntervalEXT", userptr);
|
||||
}
|
||||
static void load_GLX_MESA_pixmap_colormap( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_MESA_pixmap_colormap) return;
|
||||
glXCreateGLXPixmapMESA = (PFNGLXCREATEGLXPIXMAPMESAPROC) load("glXCreateGLXPixmapMESA", userptr);
|
||||
}
|
||||
static void load_GLX_NV_video_capture( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_NV_video_capture) return;
|
||||
glXQueryVideoCaptureDeviceNV = (PFNGLXQUERYVIDEOCAPTUREDEVICENVPROC) load("glXQueryVideoCaptureDeviceNV", userptr);
|
||||
glXEnumerateVideoCaptureDevicesNV = (PFNGLXENUMERATEVIDEOCAPTUREDEVICESNVPROC) load("glXEnumerateVideoCaptureDevicesNV", userptr);
|
||||
glXBindVideoCaptureDeviceNV = (PFNGLXBINDVIDEOCAPTUREDEVICENVPROC) load("glXBindVideoCaptureDeviceNV", userptr);
|
||||
glXLockVideoCaptureDeviceNV = (PFNGLXLOCKVIDEOCAPTUREDEVICENVPROC) load("glXLockVideoCaptureDeviceNV", userptr);
|
||||
glXReleaseVideoCaptureDeviceNV = (PFNGLXRELEASEVIDEOCAPTUREDEVICENVPROC) load("glXReleaseVideoCaptureDeviceNV", userptr);
|
||||
}
|
||||
static void load_GLX_NV_swap_group( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_NV_swap_group) return;
|
||||
glXQueryFrameCountNV = (PFNGLXQUERYFRAMECOUNTNVPROC) load("glXQueryFrameCountNV", userptr);
|
||||
glXQueryMaxSwapGroupsNV = (PFNGLXQUERYMAXSWAPGROUPSNVPROC) load("glXQueryMaxSwapGroupsNV", userptr);
|
||||
glXResetFrameCountNV = (PFNGLXRESETFRAMECOUNTNVPROC) load("glXResetFrameCountNV", userptr);
|
||||
glXJoinSwapGroupNV = (PFNGLXJOINSWAPGROUPNVPROC) load("glXJoinSwapGroupNV", userptr);
|
||||
glXBindSwapBarrierNV = (PFNGLXBINDSWAPBARRIERNVPROC) load("glXBindSwapBarrierNV", userptr);
|
||||
glXQuerySwapGroupNV = (PFNGLXQUERYSWAPGROUPNVPROC) load("glXQuerySwapGroupNV", userptr);
|
||||
}
|
||||
static void load_GLX_EXT_texture_from_pixmap( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_EXT_texture_from_pixmap) return;
|
||||
glXReleaseTexImageEXT = (PFNGLXRELEASETEXIMAGEEXTPROC) load("glXReleaseTexImageEXT", userptr);
|
||||
glXBindTexImageEXT = (PFNGLXBINDTEXIMAGEEXTPROC) load("glXBindTexImageEXT", userptr);
|
||||
}
|
||||
static void load_GLX_SUN_get_transparent_index( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_SUN_get_transparent_index) return;
|
||||
glXGetTransparentIndexSUN = (PFNGLXGETTRANSPARENTINDEXSUNPROC) load("glXGetTransparentIndexSUN", userptr);
|
||||
}
|
||||
static void load_GLX_MESA_release_buffers( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_MESA_release_buffers) return;
|
||||
glXReleaseBuffersMESA = (PFNGLXRELEASEBUFFERSMESAPROC) load("glXReleaseBuffersMESA", userptr);
|
||||
}
|
||||
static void load_GLX_NV_delay_before_swap( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_NV_delay_before_swap) return;
|
||||
glXDelayBeforeSwapNV = (PFNGLXDELAYBEFORESWAPNVPROC) load("glXDelayBeforeSwapNV", userptr);
|
||||
}
|
||||
static void load_GLX_MESA_agp_offset( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_MESA_agp_offset) return;
|
||||
glXGetAGPOffsetMESA = (PFNGLXGETAGPOFFSETMESAPROC) load("glXGetAGPOffsetMESA", userptr);
|
||||
}
|
||||
static void load_GLX_SGI_swap_control( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_SGI_swap_control) return;
|
||||
glXSwapIntervalSGI = (PFNGLXSWAPINTERVALSGIPROC) load("glXSwapIntervalSGI", userptr);
|
||||
}
|
||||
static void load_GLX_EXT_import_context( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_EXT_import_context) return;
|
||||
glXGetCurrentDisplayEXT = (PFNGLXGETCURRENTDISPLAYEXTPROC) load("glXGetCurrentDisplayEXT", userptr);
|
||||
glXImportContextEXT = (PFNGLXIMPORTCONTEXTEXTPROC) load("glXImportContextEXT", userptr);
|
||||
glXFreeContextEXT = (PFNGLXFREECONTEXTEXTPROC) load("glXFreeContextEXT", userptr);
|
||||
glXGetContextIDEXT = (PFNGLXGETCONTEXTIDEXTPROC) load("glXGetContextIDEXT", userptr);
|
||||
glXQueryContextInfoEXT = (PFNGLXQUERYCONTEXTINFOEXTPROC) load("glXQueryContextInfoEXT", userptr);
|
||||
}
|
||||
static void load_GLX_SGI_video_sync( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_SGI_video_sync) return;
|
||||
glXGetVideoSyncSGI = (PFNGLXGETVIDEOSYNCSGIPROC) load("glXGetVideoSyncSGI", userptr);
|
||||
glXWaitVideoSyncSGI = (PFNGLXWAITVIDEOSYNCSGIPROC) load("glXWaitVideoSyncSGI", userptr);
|
||||
}
|
||||
static void load_GLX_SGI_cushion( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_SGI_cushion) return;
|
||||
glXCushionSGI = (PFNGLXCUSHIONSGIPROC) load("glXCushionSGI", userptr);
|
||||
}
|
||||
static void load_GLX_SGIX_fbconfig( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_SGIX_fbconfig) return;
|
||||
glXGetFBConfigAttribSGIX = (PFNGLXGETFBCONFIGATTRIBSGIXPROC) load("glXGetFBConfigAttribSGIX", userptr);
|
||||
glXCreateGLXPixmapWithConfigSGIX = (PFNGLXCREATEGLXPIXMAPWITHCONFIGSGIXPROC) load("glXCreateGLXPixmapWithConfigSGIX", userptr);
|
||||
glXCreateContextWithConfigSGIX = (PFNGLXCREATECONTEXTWITHCONFIGSGIXPROC) load("glXCreateContextWithConfigSGIX", userptr);
|
||||
glXGetVisualFromFBConfigSGIX = (PFNGLXGETVISUALFROMFBCONFIGSGIXPROC) load("glXGetVisualFromFBConfigSGIX", userptr);
|
||||
glXChooseFBConfigSGIX = (PFNGLXCHOOSEFBCONFIGSGIXPROC) load("glXChooseFBConfigSGIX", userptr);
|
||||
glXGetFBConfigFromVisualSGIX = (PFNGLXGETFBCONFIGFROMVISUALSGIXPROC) load("glXGetFBConfigFromVisualSGIX", userptr);
|
||||
}
|
||||
static void load_GLX_NV_copy_buffer( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_NV_copy_buffer) return;
|
||||
glXNamedCopyBufferSubDataNV = (PFNGLXNAMEDCOPYBUFFERSUBDATANVPROC) load("glXNamedCopyBufferSubDataNV", userptr);
|
||||
glXCopyBufferSubDataNV = (PFNGLXCOPYBUFFERSUBDATANVPROC) load("glXCopyBufferSubDataNV", userptr);
|
||||
}
|
||||
static void load_GLX_ARB_create_context( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_ARB_create_context) return;
|
||||
glXCreateContextAttribsARB = (PFNGLXCREATECONTEXTATTRIBSARBPROC) load("glXCreateContextAttribsARB", userptr);
|
||||
}
|
||||
static void load_GLX_AMD_gpu_association( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_AMD_gpu_association) return;
|
||||
glXCreateAssociatedContextAttribsAMD = (PFNGLXCREATEASSOCIATEDCONTEXTATTRIBSAMDPROC) load("glXCreateAssociatedContextAttribsAMD", userptr);
|
||||
glXBlitContextFramebufferAMD = (PFNGLXBLITCONTEXTFRAMEBUFFERAMDPROC) load("glXBlitContextFramebufferAMD", userptr);
|
||||
glXGetCurrentAssociatedContextAMD = (PFNGLXGETCURRENTASSOCIATEDCONTEXTAMDPROC) load("glXGetCurrentAssociatedContextAMD", userptr);
|
||||
glXGetContextGPUIDAMD = (PFNGLXGETCONTEXTGPUIDAMDPROC) load("glXGetContextGPUIDAMD", userptr);
|
||||
glXMakeAssociatedContextCurrentAMD = (PFNGLXMAKEASSOCIATEDCONTEXTCURRENTAMDPROC) load("glXMakeAssociatedContextCurrentAMD", userptr);
|
||||
glXGetGPUIDsAMD = (PFNGLXGETGPUIDSAMDPROC) load("glXGetGPUIDsAMD", userptr);
|
||||
glXCreateAssociatedContextAMD = (PFNGLXCREATEASSOCIATEDCONTEXTAMDPROC) load("glXCreateAssociatedContextAMD", userptr);
|
||||
glXDeleteAssociatedContextAMD = (PFNGLXDELETEASSOCIATEDCONTEXTAMDPROC) load("glXDeleteAssociatedContextAMD", userptr);
|
||||
glXGetGPUInfoAMD = (PFNGLXGETGPUINFOAMDPROC) load("glXGetGPUInfoAMD", userptr);
|
||||
}
|
||||
static void load_GLX_MESA_query_renderer( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_MESA_query_renderer) return;
|
||||
glXQueryCurrentRendererStringMESA = (PFNGLXQUERYCURRENTRENDERERSTRINGMESAPROC) load("glXQueryCurrentRendererStringMESA", userptr);
|
||||
glXQueryCurrentRendererIntegerMESA = (PFNGLXQUERYCURRENTRENDERERINTEGERMESAPROC) load("glXQueryCurrentRendererIntegerMESA", userptr);
|
||||
glXQueryRendererStringMESA = (PFNGLXQUERYRENDERERSTRINGMESAPROC) load("glXQueryRendererStringMESA", userptr);
|
||||
glXQueryRendererIntegerMESA = (PFNGLXQUERYRENDERERINTEGERMESAPROC) load("glXQueryRendererIntegerMESA", userptr);
|
||||
}
|
||||
static void load_GLX_MESA_swap_control( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_MESA_swap_control) return;
|
||||
glXGetSwapIntervalMESA = (PFNGLXGETSWAPINTERVALMESAPROC) load("glXGetSwapIntervalMESA", userptr);
|
||||
glXSwapIntervalMESA = (PFNGLXSWAPINTERVALMESAPROC) load("glXSwapIntervalMESA", userptr);
|
||||
}
|
||||
static void load_GLX_SGIX_video_resize( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_SGIX_video_resize) return;
|
||||
glXBindChannelToWindowSGIX = (PFNGLXBINDCHANNELTOWINDOWSGIXPROC) load("glXBindChannelToWindowSGIX", userptr);
|
||||
glXChannelRectSyncSGIX = (PFNGLXCHANNELRECTSYNCSGIXPROC) load("glXChannelRectSyncSGIX", userptr);
|
||||
glXQueryChannelDeltasSGIX = (PFNGLXQUERYCHANNELDELTASSGIXPROC) load("glXQueryChannelDeltasSGIX", userptr);
|
||||
glXQueryChannelRectSGIX = (PFNGLXQUERYCHANNELRECTSGIXPROC) load("glXQueryChannelRectSGIX", userptr);
|
||||
glXChannelRectSGIX = (PFNGLXCHANNELRECTSGIXPROC) load("glXChannelRectSGIX", userptr);
|
||||
}
|
||||
static void load_GLX_NV_video_out( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_NV_video_out) return;
|
||||
glXGetVideoInfoNV = (PFNGLXGETVIDEOINFONVPROC) load("glXGetVideoInfoNV", userptr);
|
||||
glXSendPbufferToVideoNV = (PFNGLXSENDPBUFFERTOVIDEONVPROC) load("glXSendPbufferToVideoNV", userptr);
|
||||
glXReleaseVideoImageNV = (PFNGLXRELEASEVIDEOIMAGENVPROC) load("glXReleaseVideoImageNV", userptr);
|
||||
glXBindVideoImageNV = (PFNGLXBINDVIDEOIMAGENVPROC) load("glXBindVideoImageNV", userptr);
|
||||
glXReleaseVideoDeviceNV = (PFNGLXRELEASEVIDEODEVICENVPROC) load("glXReleaseVideoDeviceNV", userptr);
|
||||
glXGetVideoDeviceNV = (PFNGLXGETVIDEODEVICENVPROC) load("glXGetVideoDeviceNV", userptr);
|
||||
}
|
||||
static void load_GLX_MESA_set_3dfx_mode( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_MESA_set_3dfx_mode) return;
|
||||
glXSet3DfxModeMESA = (PFNGLXSET3DFXMODEMESAPROC) load("glXSet3DfxModeMESA", userptr);
|
||||
}
|
||||
static void load_GLX_ARB_get_proc_address( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_ARB_get_proc_address) return;
|
||||
glXGetProcAddressARB = (PFNGLXGETPROCADDRESSARBPROC) load("glXGetProcAddressARB", userptr);
|
||||
}
|
||||
static void load_GLX_NV_copy_image( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_NV_copy_image) return;
|
||||
glXCopyImageSubDataNV = (PFNGLXCOPYIMAGESUBDATANVPROC) load("glXCopyImageSubDataNV", userptr);
|
||||
}
|
||||
static void load_GLX_NV_present_video( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_NV_present_video) return;
|
||||
glXBindVideoDeviceNV = (PFNGLXBINDVIDEODEVICENVPROC) load("glXBindVideoDeviceNV", userptr);
|
||||
glXEnumerateVideoDevicesNV = (PFNGLXENUMERATEVIDEODEVICESNVPROC) load("glXEnumerateVideoDevicesNV", userptr);
|
||||
}
|
||||
static void load_GLX_SGIX_swap_barrier( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_SGIX_swap_barrier) return;
|
||||
glXBindSwapBarrierSGIX = (PFNGLXBINDSWAPBARRIERSGIXPROC) load("glXBindSwapBarrierSGIX", userptr);
|
||||
glXQueryMaxSwapBarriersSGIX = (PFNGLXQUERYMAXSWAPBARRIERSSGIXPROC) load("glXQueryMaxSwapBarriersSGIX", userptr);
|
||||
}
|
||||
static void load_GLX_SGIX_swap_group( GLADuserptrloadfunc load, void* userptr) {
|
||||
if(!GLAD_GLX_SGIX_swap_group) return;
|
||||
glXJoinSwapGroupSGIX = (PFNGLXJOINSWAPGROUPSGIXPROC) load("glXJoinSwapGroupSGIX", userptr);
|
||||
}
|
||||
|
||||
|
||||
|
||||
static int has_ext(Display *display, int screen, const char *ext) {
|
||||
const char *terminator;
|
||||
const char *loc;
|
||||
const char *extensions;
|
||||
|
||||
if(!GLAD_GLX_VERSION_1_1)
|
||||
return 0;
|
||||
|
||||
extensions = glXQueryExtensionsString(display, screen);
|
||||
|
||||
if(extensions == NULL || ext == NULL)
|
||||
return 0;
|
||||
|
||||
while(1) {
|
||||
loc = strstr(extensions, ext);
|
||||
if(loc == NULL)
|
||||
break;
|
||||
|
||||
terminator = loc + strlen(ext);
|
||||
if((loc == extensions || *(loc - 1) == ' ') &&
|
||||
(*terminator == ' ' || *terminator == '\0'))
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
extensions = terminator;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static GLADapiproc glad_glx_get_proc_from_userptr(const char* name, void *userptr) {
|
||||
return (GLAD_GNUC_EXTENSION (GLADapiproc (*)(const char *name)) userptr)(name);
|
||||
}
|
||||
|
||||
static int find_extensionsGLX(Display *display, int screen) {
|
||||
GLAD_GLX_MESA_copy_sub_buffer = has_ext(display, screen, "GLX_MESA_copy_sub_buffer");
|
||||
GLAD_GLX_EXT_create_context_es_profile = has_ext(display, screen, "GLX_EXT_create_context_es_profile");
|
||||
GLAD_GLX_SGIX_pbuffer = has_ext(display, screen, "GLX_SGIX_pbuffer");
|
||||
GLAD_GLX_SGI_make_current_read = has_ext(display, screen, "GLX_SGI_make_current_read");
|
||||
GLAD_GLX_OML_sync_control = has_ext(display, screen, "GLX_OML_sync_control");
|
||||
GLAD_GLX_SGIX_hyperpipe = has_ext(display, screen, "GLX_SGIX_hyperpipe");
|
||||
GLAD_GLX_INTEL_swap_event = has_ext(display, screen, "GLX_INTEL_swap_event");
|
||||
GLAD_GLX_EXT_swap_control = has_ext(display, screen, "GLX_EXT_swap_control");
|
||||
GLAD_GLX_NV_robustness_video_memory_purge = has_ext(display, screen, "GLX_NV_robustness_video_memory_purge");
|
||||
GLAD_GLX_MESA_pixmap_colormap = has_ext(display, screen, "GLX_MESA_pixmap_colormap");
|
||||
GLAD_GLX_ARB_fbconfig_float = has_ext(display, screen, "GLX_ARB_fbconfig_float");
|
||||
GLAD_GLX_EXT_fbconfig_packed_float = has_ext(display, screen, "GLX_EXT_fbconfig_packed_float");
|
||||
GLAD_GLX_OML_swap_method = has_ext(display, screen, "GLX_OML_swap_method");
|
||||
GLAD_GLX_NV_video_capture = has_ext(display, screen, "GLX_NV_video_capture");
|
||||
GLAD_GLX_ARB_robustness_application_isolation = has_ext(display, screen, "GLX_ARB_robustness_application_isolation");
|
||||
GLAD_GLX_ARB_create_context_robustness = has_ext(display, screen, "GLX_ARB_create_context_robustness");
|
||||
GLAD_GLX_EXT_visual_rating = has_ext(display, screen, "GLX_EXT_visual_rating");
|
||||
GLAD_GLX_NV_swap_group = has_ext(display, screen, "GLX_NV_swap_group");
|
||||
GLAD_GLX_EXT_texture_from_pixmap = has_ext(display, screen, "GLX_EXT_texture_from_pixmap");
|
||||
GLAD_GLX_SUN_get_transparent_index = has_ext(display, screen, "GLX_SUN_get_transparent_index");
|
||||
GLAD_GLX_MESA_release_buffers = has_ext(display, screen, "GLX_MESA_release_buffers");
|
||||
GLAD_GLX_NV_delay_before_swap = has_ext(display, screen, "GLX_NV_delay_before_swap");
|
||||
GLAD_GLX_EXT_buffer_age = has_ext(display, screen, "GLX_EXT_buffer_age");
|
||||
GLAD_GLX_MESA_agp_offset = has_ext(display, screen, "GLX_MESA_agp_offset");
|
||||
GLAD_GLX_EXT_visual_info = has_ext(display, screen, "GLX_EXT_visual_info");
|
||||
GLAD_GLX_SGI_swap_control = has_ext(display, screen, "GLX_SGI_swap_control");
|
||||
GLAD_GLX_EXT_import_context = has_ext(display, screen, "GLX_EXT_import_context");
|
||||
GLAD_GLX_SGI_video_sync = has_ext(display, screen, "GLX_SGI_video_sync");
|
||||
GLAD_GLX_3DFX_multisample = has_ext(display, screen, "GLX_3DFX_multisample");
|
||||
GLAD_GLX_ARB_multisample = has_ext(display, screen, "GLX_ARB_multisample");
|
||||
GLAD_GLX_EXT_framebuffer_sRGB = has_ext(display, screen, "GLX_EXT_framebuffer_sRGB");
|
||||
GLAD_GLX_SGI_cushion = has_ext(display, screen, "GLX_SGI_cushion");
|
||||
GLAD_GLX_ARB_robustness_share_group_isolation = has_ext(display, screen, "GLX_ARB_robustness_share_group_isolation");
|
||||
GLAD_GLX_SGIX_fbconfig = has_ext(display, screen, "GLX_SGIX_fbconfig");
|
||||
GLAD_GLX_NV_copy_buffer = has_ext(display, screen, "GLX_NV_copy_buffer");
|
||||
GLAD_GLX_SGIX_visual_select_group = has_ext(display, screen, "GLX_SGIX_visual_select_group");
|
||||
GLAD_GLX_EXT_swap_control_tear = has_ext(display, screen, "GLX_EXT_swap_control_tear");
|
||||
GLAD_GLX_ARB_create_context = has_ext(display, screen, "GLX_ARB_create_context");
|
||||
GLAD_GLX_AMD_gpu_association = has_ext(display, screen, "GLX_AMD_gpu_association");
|
||||
GLAD_GLX_MESA_query_renderer = has_ext(display, screen, "GLX_MESA_query_renderer");
|
||||
GLAD_GLX_EXT_create_context_es2_profile = has_ext(display, screen, "GLX_EXT_create_context_es2_profile");
|
||||
GLAD_GLX_MESA_swap_control = has_ext(display, screen, "GLX_MESA_swap_control");
|
||||
GLAD_GLX_SGIX_video_resize = has_ext(display, screen, "GLX_SGIX_video_resize");
|
||||
GLAD_GLX_ARB_context_flush_control = has_ext(display, screen, "GLX_ARB_context_flush_control");
|
||||
GLAD_GLX_NV_video_out = has_ext(display, screen, "GLX_NV_video_out");
|
||||
GLAD_GLX_EXT_no_config_context = has_ext(display, screen, "GLX_EXT_no_config_context");
|
||||
GLAD_GLX_SGIS_blended_overlay = has_ext(display, screen, "GLX_SGIS_blended_overlay");
|
||||
GLAD_GLX_EXT_stereo_tree = has_ext(display, screen, "GLX_EXT_stereo_tree");
|
||||
GLAD_GLX_ARB_create_context_no_error = has_ext(display, screen, "GLX_ARB_create_context_no_error");
|
||||
GLAD_GLX_EXT_libglvnd = has_ext(display, screen, "GLX_EXT_libglvnd");
|
||||
GLAD_GLX_ARB_create_context_profile = has_ext(display, screen, "GLX_ARB_create_context_profile");
|
||||
GLAD_GLX_NV_float_buffer = has_ext(display, screen, "GLX_NV_float_buffer");
|
||||
GLAD_GLX_MESA_set_3dfx_mode = has_ext(display, screen, "GLX_MESA_set_3dfx_mode");
|
||||
GLAD_GLX_ARB_framebuffer_sRGB = has_ext(display, screen, "GLX_ARB_framebuffer_sRGB");
|
||||
GLAD_GLX_ARB_get_proc_address = has_ext(display, screen, "GLX_ARB_get_proc_address");
|
||||
GLAD_GLX_SGIS_shared_multisample = has_ext(display, screen, "GLX_SGIS_shared_multisample");
|
||||
GLAD_GLX_NV_copy_image = has_ext(display, screen, "GLX_NV_copy_image");
|
||||
GLAD_GLX_NV_present_video = has_ext(display, screen, "GLX_NV_present_video");
|
||||
GLAD_GLX_SGIX_swap_barrier = has_ext(display, screen, "GLX_SGIX_swap_barrier");
|
||||
GLAD_GLX_SGIS_multisample = has_ext(display, screen, "GLX_SGIS_multisample");
|
||||
GLAD_GLX_SGIX_swap_group = has_ext(display, screen, "GLX_SGIX_swap_group");
|
||||
GLAD_GLX_ARB_vertex_buffer_object = has_ext(display, screen, "GLX_ARB_vertex_buffer_object");
|
||||
GLAD_GLX_NV_multisample_coverage = has_ext(display, screen, "GLX_NV_multisample_coverage");
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int find_coreGLX(Display **display, int *screen) {
|
||||
X11Struct x11;
|
||||
initX11Struct(&x11);
|
||||
int major = 0, minor = 0;
|
||||
if(*display == NULL) {
|
||||
*display = x11.XOpenDisplay(0);
|
||||
if (*display == NULL) {
|
||||
return 0;
|
||||
}
|
||||
*screen = x11.XScreenNumberOfScreen(x11.XDefaultScreenOfDisplay(*display));
|
||||
}
|
||||
glXQueryVersion(*display, &major, &minor);
|
||||
GLAD_GLX_VERSION_1_0 = (major == 1 && minor >= 0) || major > 1;
|
||||
GLAD_GLX_VERSION_1_1 = (major == 1 && minor >= 1) || major > 1;
|
||||
GLAD_GLX_VERSION_1_2 = (major == 1 && minor >= 2) || major > 1;
|
||||
GLAD_GLX_VERSION_1_3 = (major == 1 && minor >= 3) || major > 1;
|
||||
GLAD_GLX_VERSION_1_4 = (major == 1 && minor >= 4) || major > 1;
|
||||
return GLAD_MAKE_VERSION(major, minor);
|
||||
}
|
||||
|
||||
int gladLoadGLXUserPtr(Display *display, int screen, GLADuserptrloadfunc load, void *userptr) {
|
||||
int version;
|
||||
glXQueryVersion = (PFNGLXQUERYVERSIONPROC) load("glXQueryVersion", userptr);
|
||||
if(glXQueryVersion == NULL) return 0;
|
||||
version = find_coreGLX(&display, &screen);
|
||||
|
||||
load_GLX_VERSION_1_0(load, userptr);
|
||||
load_GLX_VERSION_1_1(load, userptr);
|
||||
load_GLX_VERSION_1_2(load, userptr);
|
||||
load_GLX_VERSION_1_3(load, userptr);
|
||||
load_GLX_VERSION_1_4(load, userptr);
|
||||
|
||||
if (!find_extensionsGLX(display, screen)) return 0;
|
||||
load_GLX_MESA_copy_sub_buffer(load, userptr);
|
||||
load_GLX_SGIX_pbuffer(load, userptr);
|
||||
load_GLX_SGI_make_current_read(load, userptr);
|
||||
load_GLX_OML_sync_control(load, userptr);
|
||||
load_GLX_SGIX_hyperpipe(load, userptr);
|
||||
load_GLX_EXT_swap_control(load, userptr);
|
||||
load_GLX_MESA_pixmap_colormap(load, userptr);
|
||||
load_GLX_NV_video_capture(load, userptr);
|
||||
load_GLX_NV_swap_group(load, userptr);
|
||||
load_GLX_EXT_texture_from_pixmap(load, userptr);
|
||||
load_GLX_SUN_get_transparent_index(load, userptr);
|
||||
load_GLX_MESA_release_buffers(load, userptr);
|
||||
load_GLX_NV_delay_before_swap(load, userptr);
|
||||
load_GLX_MESA_agp_offset(load, userptr);
|
||||
load_GLX_SGI_swap_control(load, userptr);
|
||||
load_GLX_EXT_import_context(load, userptr);
|
||||
load_GLX_SGI_video_sync(load, userptr);
|
||||
load_GLX_SGI_cushion(load, userptr);
|
||||
load_GLX_SGIX_fbconfig(load, userptr);
|
||||
load_GLX_NV_copy_buffer(load, userptr);
|
||||
load_GLX_ARB_create_context(load, userptr);
|
||||
load_GLX_AMD_gpu_association(load, userptr);
|
||||
load_GLX_MESA_query_renderer(load, userptr);
|
||||
load_GLX_MESA_swap_control(load, userptr);
|
||||
load_GLX_SGIX_video_resize(load, userptr);
|
||||
load_GLX_NV_video_out(load, userptr);
|
||||
load_GLX_MESA_set_3dfx_mode(load, userptr);
|
||||
load_GLX_ARB_get_proc_address(load, userptr);
|
||||
load_GLX_NV_copy_image(load, userptr);
|
||||
load_GLX_NV_present_video(load, userptr);
|
||||
load_GLX_SGIX_swap_barrier(load, userptr);
|
||||
load_GLX_SGIX_swap_group(load, userptr);
|
||||
|
||||
return version;
|
||||
}
|
||||
|
||||
int gladLoadGLX(Display *display, int screen, GLADloadfunc load) {
|
||||
return gladLoadGLXUserPtr(display, screen, glad_glx_get_proc_from_userptr, GLAD_GNUC_EXTENSION (void*) load);
|
||||
}
|
||||
|
||||
|
||||
#ifdef GLAD_GLX
|
||||
|
||||
#ifndef GLAD_LOADER_LIBRARY_C_
|
||||
#define GLAD_LOADER_LIBRARY_C_
|
||||
|
||||
#include <stddef.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#if GLAD_PLATFORM_WIN32
|
||||
#include <windows.h>
|
||||
#else
|
||||
#include <dlfcn.h>
|
||||
#endif
|
||||
|
||||
|
||||
static void* glad_get_dlopen_handle(const char *lib_names[], int length) {
|
||||
void *handle = NULL;
|
||||
int i;
|
||||
|
||||
for (i = 0; i < length; ++i) {
|
||||
#if GLAD_PLATFORM_WIN32
|
||||
#if GLAD_PLATFORM_UWP
|
||||
size_t buffer_size = (strlen(lib_names[i]) + 1) * sizeof(WCHAR);
|
||||
LPWSTR buffer = (LPWSTR) malloc(buffer_size);
|
||||
if (buffer != NULL) {
|
||||
int ret = MultiByteToWideChar(CP_ACP, 0, lib_names[i], -1, buffer, buffer_size);
|
||||
if (ret != 0) {
|
||||
handle = (void*) LoadPackagedLibrary(buffer, 0);
|
||||
}
|
||||
free((void*) buffer);
|
||||
}
|
||||
#else
|
||||
handle = (void*) LoadLibraryA(lib_names[i]);
|
||||
#endif
|
||||
#else
|
||||
handle = dlopen(lib_names[i], RTLD_LAZY | RTLD_LOCAL);
|
||||
#endif
|
||||
if (handle != NULL) {
|
||||
return handle;
|
||||
}
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static void glad_close_dlopen_handle(void* handle) {
|
||||
if (handle != NULL) {
|
||||
#if GLAD_PLATFORM_WIN32
|
||||
FreeLibrary((HMODULE) handle);
|
||||
#else
|
||||
dlclose(handle);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
static GLADapiproc glad_dlsym_handle(void* handle, const char *name) {
|
||||
if (handle == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
#if GLAD_PLATFORM_WIN32
|
||||
return (GLADapiproc) GetProcAddress((HMODULE) handle, name);
|
||||
#else
|
||||
return GLAD_GNUC_EXTENSION (GLADapiproc) dlsym(handle, name);
|
||||
#endif
|
||||
}
|
||||
|
||||
#endif /* GLAD_LOADER_LIBRARY_C_ */
|
||||
|
||||
typedef void* (GLAD_API_PTR *GLADglxprocaddrfunc)(const char*);
|
||||
|
||||
static GLADapiproc glad_glx_get_proc(const char *name, void *userptr) {
|
||||
return GLAD_GNUC_EXTENSION ((GLADapiproc (*)(const char *name)) userptr)(name);
|
||||
}
|
||||
|
||||
static void* _glx_handle;
|
||||
|
||||
int gladLoaderLoadGLX(Display *display, int screen) {
|
||||
static const char *NAMES[] = {
|
||||
#if defined __CYGWIN__
|
||||
"libGL-1.so",
|
||||
#endif
|
||||
"libGL.so.1",
|
||||
"libGL.so"
|
||||
};
|
||||
|
||||
int version = 0;
|
||||
int did_load = 0;
|
||||
GLADglxprocaddrfunc loader;
|
||||
|
||||
if (_glx_handle == NULL) {
|
||||
_glx_handle = glad_get_dlopen_handle(NAMES, sizeof(NAMES) / sizeof(NAMES[0]));
|
||||
did_load = _glx_handle != NULL;
|
||||
}
|
||||
|
||||
if (_glx_handle != NULL) {
|
||||
loader = (GLADglxprocaddrfunc) glad_dlsym_handle(_glx_handle, "glXGetProcAddressARB");
|
||||
if (loader != NULL) {
|
||||
version = gladLoadGLXUserPtr(display, screen, glad_glx_get_proc, GLAD_GNUC_EXTENSION (void*) loader);
|
||||
}
|
||||
|
||||
if (!version && did_load) {
|
||||
glad_close_dlopen_handle(_glx_handle);
|
||||
_glx_handle = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
return version;
|
||||
}
|
||||
|
||||
void gladLoaderUnloadGLX() {
|
||||
if (_glx_handle != NULL) {
|
||||
glad_close_dlopen_handle(_glx_handle);
|
||||
_glx_handle = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
#endif /* GLAD_GLX */
|
|
@ -1,574 +0,0 @@
|
|||
#ifndef LINMATH_H
|
||||
#define LINMATH_H
|
||||
|
||||
#include <math.h>
|
||||
|
||||
#ifdef _MSC_VER
|
||||
#define inline __inline
|
||||
#endif
|
||||
|
||||
#define LINMATH_H_DEFINE_VEC(n) \
|
||||
typedef float vec##n[n]; \
|
||||
static inline void vec##n##_add(vec##n r, vec##n const a, vec##n const b) \
|
||||
{ \
|
||||
int i; \
|
||||
for(i=0; i<n; ++i) \
|
||||
r[i] = a[i] + b[i]; \
|
||||
} \
|
||||
static inline void vec##n##_sub(vec##n r, vec##n const a, vec##n const b) \
|
||||
{ \
|
||||
int i; \
|
||||
for(i=0; i<n; ++i) \
|
||||
r[i] = a[i] - b[i]; \
|
||||
} \
|
||||
static inline void vec##n##_scale(vec##n r, vec##n const v, float const s) \
|
||||
{ \
|
||||
int i; \
|
||||
for(i=0; i<n; ++i) \
|
||||
r[i] = v[i] * s; \
|
||||
} \
|
||||
static inline float vec##n##_mul_inner(vec##n const a, vec##n const b) \
|
||||
{ \
|
||||
float p = 0.; \
|
||||
int i; \
|
||||
for(i=0; i<n; ++i) \
|
||||
p += b[i]*a[i]; \
|
||||
return p; \
|
||||
} \
|
||||
static inline float vec##n##_len(vec##n const v) \
|
||||
{ \
|
||||
return (float) sqrt(vec##n##_mul_inner(v,v)); \
|
||||
} \
|
||||
static inline void vec##n##_norm(vec##n r, vec##n const v) \
|
||||
{ \
|
||||
float k = 1.f / vec##n##_len(v); \
|
||||
vec##n##_scale(r, v, k); \
|
||||
}
|
||||
|
||||
LINMATH_H_DEFINE_VEC(2)
|
||||
LINMATH_H_DEFINE_VEC(3)
|
||||
LINMATH_H_DEFINE_VEC(4)
|
||||
|
||||
static inline void vec3_mul_cross(vec3 r, vec3 const a, vec3 const b)
|
||||
{
|
||||
r[0] = a[1]*b[2] - a[2]*b[1];
|
||||
r[1] = a[2]*b[0] - a[0]*b[2];
|
||||
r[2] = a[0]*b[1] - a[1]*b[0];
|
||||
}
|
||||
|
||||
static inline void vec3_reflect(vec3 r, vec3 const v, vec3 const n)
|
||||
{
|
||||
float p = 2.f*vec3_mul_inner(v, n);
|
||||
int i;
|
||||
for(i=0;i<3;++i)
|
||||
r[i] = v[i] - p*n[i];
|
||||
}
|
||||
|
||||
static inline void vec4_mul_cross(vec4 r, vec4 a, vec4 b)
|
||||
{
|
||||
r[0] = a[1]*b[2] - a[2]*b[1];
|
||||
r[1] = a[2]*b[0] - a[0]*b[2];
|
||||
r[2] = a[0]*b[1] - a[1]*b[0];
|
||||
r[3] = 1.f;
|
||||
}
|
||||
|
||||
static inline void vec4_reflect(vec4 r, vec4 v, vec4 n)
|
||||
{
|
||||
float p = 2.f*vec4_mul_inner(v, n);
|
||||
int i;
|
||||
for(i=0;i<4;++i)
|
||||
r[i] = v[i] - p*n[i];
|
||||
}
|
||||
|
||||
typedef vec4 mat4x4[4];
|
||||
static inline void mat4x4_identity(mat4x4 M)
|
||||
{
|
||||
int i, j;
|
||||
for(i=0; i<4; ++i)
|
||||
for(j=0; j<4; ++j)
|
||||
M[i][j] = i==j ? 1.f : 0.f;
|
||||
}
|
||||
static inline void mat4x4_dup(mat4x4 M, mat4x4 N)
|
||||
{
|
||||
int i, j;
|
||||
for(i=0; i<4; ++i)
|
||||
for(j=0; j<4; ++j)
|
||||
M[i][j] = N[i][j];
|
||||
}
|
||||
static inline void mat4x4_row(vec4 r, mat4x4 M, int i)
|
||||
{
|
||||
int k;
|
||||
for(k=0; k<4; ++k)
|
||||
r[k] = M[k][i];
|
||||
}
|
||||
static inline void mat4x4_col(vec4 r, mat4x4 M, int i)
|
||||
{
|
||||
int k;
|
||||
for(k=0; k<4; ++k)
|
||||
r[k] = M[i][k];
|
||||
}
|
||||
static inline void mat4x4_transpose(mat4x4 M, mat4x4 N)
|
||||
{
|
||||
int i, j;
|
||||
for(j=0; j<4; ++j)
|
||||
for(i=0; i<4; ++i)
|
||||
M[i][j] = N[j][i];
|
||||
}
|
||||
static inline void mat4x4_add(mat4x4 M, mat4x4 a, mat4x4 b)
|
||||
{
|
||||
int i;
|
||||
for(i=0; i<4; ++i)
|
||||
vec4_add(M[i], a[i], b[i]);
|
||||
}
|
||||
static inline void mat4x4_sub(mat4x4 M, mat4x4 a, mat4x4 b)
|
||||
{
|
||||
int i;
|
||||
for(i=0; i<4; ++i)
|
||||
vec4_sub(M[i], a[i], b[i]);
|
||||
}
|
||||
static inline void mat4x4_scale(mat4x4 M, mat4x4 a, float k)
|
||||
{
|
||||
int i;
|
||||
for(i=0; i<4; ++i)
|
||||
vec4_scale(M[i], a[i], k);
|
||||
}
|
||||
static inline void mat4x4_scale_aniso(mat4x4 M, mat4x4 a, float x, float y, float z)
|
||||
{
|
||||
int i;
|
||||
vec4_scale(M[0], a[0], x);
|
||||
vec4_scale(M[1], a[1], y);
|
||||
vec4_scale(M[2], a[2], z);
|
||||
for(i = 0; i < 4; ++i) {
|
||||
M[3][i] = a[3][i];
|
||||
}
|
||||
}
|
||||
static inline void mat4x4_mul(mat4x4 M, mat4x4 a, mat4x4 b)
|
||||
{
|
||||
mat4x4 temp;
|
||||
int k, r, c;
|
||||
for(c=0; c<4; ++c) for(r=0; r<4; ++r) {
|
||||
temp[c][r] = 0.f;
|
||||
for(k=0; k<4; ++k)
|
||||
temp[c][r] += a[k][r] * b[c][k];
|
||||
}
|
||||
mat4x4_dup(M, temp);
|
||||
}
|
||||
static inline void mat4x4_mul_vec4(vec4 r, mat4x4 M, vec4 v)
|
||||
{
|
||||
int i, j;
|
||||
for(j=0; j<4; ++j) {
|
||||
r[j] = 0.f;
|
||||
for(i=0; i<4; ++i)
|
||||
r[j] += M[i][j] * v[i];
|
||||
}
|
||||
}
|
||||
static inline void mat4x4_translate(mat4x4 T, float x, float y, float z)
|
||||
{
|
||||
mat4x4_identity(T);
|
||||
T[3][0] = x;
|
||||
T[3][1] = y;
|
||||
T[3][2] = z;
|
||||
}
|
||||
static inline void mat4x4_translate_in_place(mat4x4 M, float x, float y, float z)
|
||||
{
|
||||
vec4 t = {x, y, z, 0};
|
||||
vec4 r;
|
||||
int i;
|
||||
for (i = 0; i < 4; ++i) {
|
||||
mat4x4_row(r, M, i);
|
||||
M[3][i] += vec4_mul_inner(r, t);
|
||||
}
|
||||
}
|
||||
static inline void mat4x4_from_vec3_mul_outer(mat4x4 M, vec3 a, vec3 b)
|
||||
{
|
||||
int i, j;
|
||||
for(i=0; i<4; ++i) for(j=0; j<4; ++j)
|
||||
M[i][j] = i<3 && j<3 ? a[i] * b[j] : 0.f;
|
||||
}
|
||||
static inline void mat4x4_rotate(mat4x4 R, mat4x4 M, float x, float y, float z, float angle)
|
||||
{
|
||||
float s = sinf(angle);
|
||||
float c = cosf(angle);
|
||||
vec3 u = {x, y, z};
|
||||
|
||||
if(vec3_len(u) > 1e-4) {
|
||||
mat4x4 T, C, S = {{0}};
|
||||
|
||||
vec3_norm(u, u);
|
||||
mat4x4_from_vec3_mul_outer(T, u, u);
|
||||
|
||||
S[1][2] = u[0];
|
||||
S[2][1] = -u[0];
|
||||
S[2][0] = u[1];
|
||||
S[0][2] = -u[1];
|
||||
S[0][1] = u[2];
|
||||
S[1][0] = -u[2];
|
||||
|
||||
mat4x4_scale(S, S, s);
|
||||
|
||||
mat4x4_identity(C);
|
||||
mat4x4_sub(C, C, T);
|
||||
|
||||
mat4x4_scale(C, C, c);
|
||||
|
||||
mat4x4_add(T, T, C);
|
||||
mat4x4_add(T, T, S);
|
||||
|
||||
T[3][3] = 1.;
|
||||
mat4x4_mul(R, M, T);
|
||||
} else {
|
||||
mat4x4_dup(R, M);
|
||||
}
|
||||
}
|
||||
static inline void mat4x4_rotate_X(mat4x4 Q, mat4x4 M, float angle)
|
||||
{
|
||||
float s = sinf(angle);
|
||||
float c = cosf(angle);
|
||||
mat4x4 R = {
|
||||
{1.f, 0.f, 0.f, 0.f},
|
||||
{0.f, c, s, 0.f},
|
||||
{0.f, -s, c, 0.f},
|
||||
{0.f, 0.f, 0.f, 1.f}
|
||||
};
|
||||
mat4x4_mul(Q, M, R);
|
||||
}
|
||||
static inline void mat4x4_rotate_Y(mat4x4 Q, mat4x4 M, float angle)
|
||||
{
|
||||
float s = sinf(angle);
|
||||
float c = cosf(angle);
|
||||
mat4x4 R = {
|
||||
{ c, 0.f, s, 0.f},
|
||||
{ 0.f, 1.f, 0.f, 0.f},
|
||||
{ -s, 0.f, c, 0.f},
|
||||
{ 0.f, 0.f, 0.f, 1.f}
|
||||
};
|
||||
mat4x4_mul(Q, M, R);
|
||||
}
|
||||
static inline void mat4x4_rotate_Z(mat4x4 Q, mat4x4 M, float angle)
|
||||
{
|
||||
float s = sinf(angle);
|
||||
float c = cosf(angle);
|
||||
mat4x4 R = {
|
||||
{ c, s, 0.f, 0.f},
|
||||
{ -s, c, 0.f, 0.f},
|
||||
{ 0.f, 0.f, 1.f, 0.f},
|
||||
{ 0.f, 0.f, 0.f, 1.f}
|
||||
};
|
||||
mat4x4_mul(Q, M, R);
|
||||
}
|
||||
static inline void mat4x4_invert(mat4x4 T, mat4x4 M)
|
||||
{
|
||||
float idet;
|
||||
float s[6];
|
||||
float c[6];
|
||||
s[0] = M[0][0]*M[1][1] - M[1][0]*M[0][1];
|
||||
s[1] = M[0][0]*M[1][2] - M[1][0]*M[0][2];
|
||||
s[2] = M[0][0]*M[1][3] - M[1][0]*M[0][3];
|
||||
s[3] = M[0][1]*M[1][2] - M[1][1]*M[0][2];
|
||||
s[4] = M[0][1]*M[1][3] - M[1][1]*M[0][3];
|
||||
s[5] = M[0][2]*M[1][3] - M[1][2]*M[0][3];
|
||||
|
||||
c[0] = M[2][0]*M[3][1] - M[3][0]*M[2][1];
|
||||
c[1] = M[2][0]*M[3][2] - M[3][0]*M[2][2];
|
||||
c[2] = M[2][0]*M[3][3] - M[3][0]*M[2][3];
|
||||
c[3] = M[2][1]*M[3][2] - M[3][1]*M[2][2];
|
||||
c[4] = M[2][1]*M[3][3] - M[3][1]*M[2][3];
|
||||
c[5] = M[2][2]*M[3][3] - M[3][2]*M[2][3];
|
||||
|
||||
/* Assumes it is invertible */
|
||||
idet = 1.0f/( s[0]*c[5]-s[1]*c[4]+s[2]*c[3]+s[3]*c[2]-s[4]*c[1]+s[5]*c[0] );
|
||||
|
||||
T[0][0] = ( M[1][1] * c[5] - M[1][2] * c[4] + M[1][3] * c[3]) * idet;
|
||||
T[0][1] = (-M[0][1] * c[5] + M[0][2] * c[4] - M[0][3] * c[3]) * idet;
|
||||
T[0][2] = ( M[3][1] * s[5] - M[3][2] * s[4] + M[3][3] * s[3]) * idet;
|
||||
T[0][3] = (-M[2][1] * s[5] + M[2][2] * s[4] - M[2][3] * s[3]) * idet;
|
||||
|
||||
T[1][0] = (-M[1][0] * c[5] + M[1][2] * c[2] - M[1][3] * c[1]) * idet;
|
||||
T[1][1] = ( M[0][0] * c[5] - M[0][2] * c[2] + M[0][3] * c[1]) * idet;
|
||||
T[1][2] = (-M[3][0] * s[5] + M[3][2] * s[2] - M[3][3] * s[1]) * idet;
|
||||
T[1][3] = ( M[2][0] * s[5] - M[2][2] * s[2] + M[2][3] * s[1]) * idet;
|
||||
|
||||
T[2][0] = ( M[1][0] * c[4] - M[1][1] * c[2] + M[1][3] * c[0]) * idet;
|
||||
T[2][1] = (-M[0][0] * c[4] + M[0][1] * c[2] - M[0][3] * c[0]) * idet;
|
||||
T[2][2] = ( M[3][0] * s[4] - M[3][1] * s[2] + M[3][3] * s[0]) * idet;
|
||||
T[2][3] = (-M[2][0] * s[4] + M[2][1] * s[2] - M[2][3] * s[0]) * idet;
|
||||
|
||||
T[3][0] = (-M[1][0] * c[3] + M[1][1] * c[1] - M[1][2] * c[0]) * idet;
|
||||
T[3][1] = ( M[0][0] * c[3] - M[0][1] * c[1] + M[0][2] * c[0]) * idet;
|
||||
T[3][2] = (-M[3][0] * s[3] + M[3][1] * s[1] - M[3][2] * s[0]) * idet;
|
||||
T[3][3] = ( M[2][0] * s[3] - M[2][1] * s[1] + M[2][2] * s[0]) * idet;
|
||||
}
|
||||
static inline void mat4x4_orthonormalize(mat4x4 R, mat4x4 M)
|
||||
{
|
||||
float s = 1.;
|
||||
vec3 h;
|
||||
|
||||
mat4x4_dup(R, M);
|
||||
vec3_norm(R[2], R[2]);
|
||||
|
||||
s = vec3_mul_inner(R[1], R[2]);
|
||||
vec3_scale(h, R[2], s);
|
||||
vec3_sub(R[1], R[1], h);
|
||||
vec3_norm(R[2], R[2]);
|
||||
|
||||
s = vec3_mul_inner(R[1], R[2]);
|
||||
vec3_scale(h, R[2], s);
|
||||
vec3_sub(R[1], R[1], h);
|
||||
vec3_norm(R[1], R[1]);
|
||||
|
||||
s = vec3_mul_inner(R[0], R[1]);
|
||||
vec3_scale(h, R[1], s);
|
||||
vec3_sub(R[0], R[0], h);
|
||||
vec3_norm(R[0], R[0]);
|
||||
}
|
||||
|
||||
static inline void mat4x4_frustum(mat4x4 M, float l, float r, float b, float t, float n, float f)
|
||||
{
|
||||
M[0][0] = 2.f*n/(r-l);
|
||||
M[0][1] = M[0][2] = M[0][3] = 0.f;
|
||||
|
||||
M[1][1] = 2.f*n/(t-b);
|
||||
M[1][0] = M[1][2] = M[1][3] = 0.f;
|
||||
|
||||
M[2][0] = (r+l)/(r-l);
|
||||
M[2][1] = (t+b)/(t-b);
|
||||
M[2][2] = -(f+n)/(f-n);
|
||||
M[2][3] = -1.f;
|
||||
|
||||
M[3][2] = -2.f*(f*n)/(f-n);
|
||||
M[3][0] = M[3][1] = M[3][3] = 0.f;
|
||||
}
|
||||
static inline void mat4x4_ortho(mat4x4 M, float l, float r, float b, float t, float n, float f)
|
||||
{
|
||||
M[0][0] = 2.f/(r-l);
|
||||
M[0][1] = M[0][2] = M[0][3] = 0.f;
|
||||
|
||||
M[1][1] = 2.f/(t-b);
|
||||
M[1][0] = M[1][2] = M[1][3] = 0.f;
|
||||
|
||||
M[2][2] = -2.f/(f-n);
|
||||
M[2][0] = M[2][1] = M[2][3] = 0.f;
|
||||
|
||||
M[3][0] = -(r+l)/(r-l);
|
||||
M[3][1] = -(t+b)/(t-b);
|
||||
M[3][2] = -(f+n)/(f-n);
|
||||
M[3][3] = 1.f;
|
||||
}
|
||||
static inline void mat4x4_perspective(mat4x4 m, float y_fov, float aspect, float n, float f)
|
||||
{
|
||||
/* NOTE: Degrees are an unhandy unit to work with.
|
||||
* linmath.h uses radians for everything! */
|
||||
float const a = 1.f / (float) tan(y_fov / 2.f);
|
||||
|
||||
m[0][0] = a / aspect;
|
||||
m[0][1] = 0.f;
|
||||
m[0][2] = 0.f;
|
||||
m[0][3] = 0.f;
|
||||
|
||||
m[1][0] = 0.f;
|
||||
m[1][1] = a;
|
||||
m[1][2] = 0.f;
|
||||
m[1][3] = 0.f;
|
||||
|
||||
m[2][0] = 0.f;
|
||||
m[2][1] = 0.f;
|
||||
m[2][2] = -((f + n) / (f - n));
|
||||
m[2][3] = -1.f;
|
||||
|
||||
m[3][0] = 0.f;
|
||||
m[3][1] = 0.f;
|
||||
m[3][2] = -((2.f * f * n) / (f - n));
|
||||
m[3][3] = 0.f;
|
||||
}
|
||||
static inline void mat4x4_look_at(mat4x4 m, vec3 eye, vec3 center, vec3 up)
|
||||
{
|
||||
/* Adapted from Android's OpenGL Matrix.java. */
|
||||
/* See the OpenGL GLUT documentation for gluLookAt for a description */
|
||||
/* of the algorithm. We implement it in a straightforward way: */
|
||||
|
||||
/* TODO: The negation of of can be spared by swapping the order of
|
||||
* operands in the following cross products in the right way. */
|
||||
vec3 f;
|
||||
vec3 s;
|
||||
vec3 t;
|
||||
|
||||
vec3_sub(f, center, eye);
|
||||
vec3_norm(f, f);
|
||||
|
||||
vec3_mul_cross(s, f, up);
|
||||
vec3_norm(s, s);
|
||||
|
||||
vec3_mul_cross(t, s, f);
|
||||
|
||||
m[0][0] = s[0];
|
||||
m[0][1] = t[0];
|
||||
m[0][2] = -f[0];
|
||||
m[0][3] = 0.f;
|
||||
|
||||
m[1][0] = s[1];
|
||||
m[1][1] = t[1];
|
||||
m[1][2] = -f[1];
|
||||
m[1][3] = 0.f;
|
||||
|
||||
m[2][0] = s[2];
|
||||
m[2][1] = t[2];
|
||||
m[2][2] = -f[2];
|
||||
m[2][3] = 0.f;
|
||||
|
||||
m[3][0] = 0.f;
|
||||
m[3][1] = 0.f;
|
||||
m[3][2] = 0.f;
|
||||
m[3][3] = 1.f;
|
||||
|
||||
mat4x4_translate_in_place(m, -eye[0], -eye[1], -eye[2]);
|
||||
}
|
||||
|
||||
typedef float quat[4];
|
||||
static inline void quat_identity(quat q)
|
||||
{
|
||||
q[0] = q[1] = q[2] = 0.f;
|
||||
q[3] = 1.f;
|
||||
}
|
||||
static inline void quat_add(quat r, quat a, quat b)
|
||||
{
|
||||
int i;
|
||||
for(i=0; i<4; ++i)
|
||||
r[i] = a[i] + b[i];
|
||||
}
|
||||
static inline void quat_sub(quat r, quat a, quat b)
|
||||
{
|
||||
int i;
|
||||
for(i=0; i<4; ++i)
|
||||
r[i] = a[i] - b[i];
|
||||
}
|
||||
static inline void quat_mul(quat r, quat p, quat q)
|
||||
{
|
||||
vec3 w;
|
||||
vec3_mul_cross(r, p, q);
|
||||
vec3_scale(w, p, q[3]);
|
||||
vec3_add(r, r, w);
|
||||
vec3_scale(w, q, p[3]);
|
||||
vec3_add(r, r, w);
|
||||
r[3] = p[3]*q[3] - vec3_mul_inner(p, q);
|
||||
}
|
||||
static inline void quat_scale(quat r, quat v, float s)
|
||||
{
|
||||
int i;
|
||||
for(i=0; i<4; ++i)
|
||||
r[i] = v[i] * s;
|
||||
}
|
||||
static inline float quat_inner_product(quat a, quat b)
|
||||
{
|
||||
float p = 0.f;
|
||||
int i;
|
||||
for(i=0; i<4; ++i)
|
||||
p += b[i]*a[i];
|
||||
return p;
|
||||
}
|
||||
static inline void quat_conj(quat r, quat q)
|
||||
{
|
||||
int i;
|
||||
for(i=0; i<3; ++i)
|
||||
r[i] = -q[i];
|
||||
r[3] = q[3];
|
||||
}
|
||||
static inline void quat_rotate(quat r, float angle, vec3 axis) {
|
||||
int i;
|
||||
vec3 v;
|
||||
vec3_scale(v, axis, sinf(angle / 2));
|
||||
for(i=0; i<3; ++i)
|
||||
r[i] = v[i];
|
||||
r[3] = cosf(angle / 2);
|
||||
}
|
||||
#define quat_norm vec4_norm
|
||||
static inline void quat_mul_vec3(vec3 r, quat q, vec3 v)
|
||||
{
|
||||
/*
|
||||
* Method by Fabian 'ryg' Giessen (of Farbrausch)
|
||||
t = 2 * cross(q.xyz, v)
|
||||
v' = v + q.w * t + cross(q.xyz, t)
|
||||
*/
|
||||
vec3 t = {q[0], q[1], q[2]};
|
||||
vec3 u = {q[0], q[1], q[2]};
|
||||
|
||||
vec3_mul_cross(t, t, v);
|
||||
vec3_scale(t, t, 2);
|
||||
|
||||
vec3_mul_cross(u, u, t);
|
||||
vec3_scale(t, t, q[3]);
|
||||
|
||||
vec3_add(r, v, t);
|
||||
vec3_add(r, r, u);
|
||||
}
|
||||
static inline void mat4x4_from_quat(mat4x4 M, quat q)
|
||||
{
|
||||
float a = q[3];
|
||||
float b = q[0];
|
||||
float c = q[1];
|
||||
float d = q[2];
|
||||
float a2 = a*a;
|
||||
float b2 = b*b;
|
||||
float c2 = c*c;
|
||||
float d2 = d*d;
|
||||
|
||||
M[0][0] = a2 + b2 - c2 - d2;
|
||||
M[0][1] = 2.f*(b*c + a*d);
|
||||
M[0][2] = 2.f*(b*d - a*c);
|
||||
M[0][3] = 0.f;
|
||||
|
||||
M[1][0] = 2*(b*c - a*d);
|
||||
M[1][1] = a2 - b2 + c2 - d2;
|
||||
M[1][2] = 2.f*(c*d + a*b);
|
||||
M[1][3] = 0.f;
|
||||
|
||||
M[2][0] = 2.f*(b*d + a*c);
|
||||
M[2][1] = 2.f*(c*d - a*b);
|
||||
M[2][2] = a2 - b2 - c2 + d2;
|
||||
M[2][3] = 0.f;
|
||||
|
||||
M[3][0] = M[3][1] = M[3][2] = 0.f;
|
||||
M[3][3] = 1.f;
|
||||
}
|
||||
|
||||
static inline void mat4x4o_mul_quat(mat4x4 R, mat4x4 M, quat q)
|
||||
{
|
||||
/* XXX: The way this is written only works for othogonal matrices. */
|
||||
/* TODO: Take care of non-orthogonal case. */
|
||||
quat_mul_vec3(R[0], q, M[0]);
|
||||
quat_mul_vec3(R[1], q, M[1]);
|
||||
quat_mul_vec3(R[2], q, M[2]);
|
||||
|
||||
R[3][0] = R[3][1] = R[3][2] = 0.f;
|
||||
R[3][3] = 1.f;
|
||||
}
|
||||
static inline void quat_from_mat4x4(quat q, mat4x4 M)
|
||||
{
|
||||
float r=0.f;
|
||||
int i;
|
||||
|
||||
int perm[] = { 0, 1, 2, 0, 1 };
|
||||
int *p = perm;
|
||||
|
||||
for(i = 0; i<3; i++) {
|
||||
float m = M[i][i];
|
||||
if( m < r )
|
||||
continue;
|
||||
m = r;
|
||||
p = &perm[i];
|
||||
}
|
||||
|
||||
r = (float) sqrt(1.f + M[p[0]][p[0]] - M[p[1]][p[1]] - M[p[2]][p[2]] );
|
||||
|
||||
if(r < 1e-6) {
|
||||
q[0] = 1.f;
|
||||
q[1] = q[2] = q[3] = 0.f;
|
||||
return;
|
||||
}
|
||||
|
||||
q[0] = r/2.f;
|
||||
q[1] = (M[p[0]][p[1]] - M[p[1]][p[0]])/(2.f*r);
|
||||
q[2] = (M[p[2]][p[0]] - M[p[0]][p[2]])/(2.f*r);
|
||||
q[3] = (M[p[2]][p[1]] - M[p[1]][p[2]])/(2.f*r);
|
||||
}
|
||||
|
||||
#endif
|
|
@ -1,24 +0,0 @@
|
|||
import json
|
||||
import os
|
||||
|
||||
pose_path = '/home/jerry/Desktop/Data/1CzjpjNF8qk/points'
|
||||
|
||||
pose_output = '/home/jerry/Desktop/view3d/realenv/depth/posefile'
|
||||
|
||||
fout = open(pose_output, 'w')
|
||||
|
||||
all_paths = []
|
||||
for posefile in os.listdir(pose_path):
|
||||
all_paths.append(posefile)
|
||||
|
||||
all_paths = sorted(all_paths)
|
||||
|
||||
for posefile in all_paths:
|
||||
with open(os.path.join(pose_path, posefile)) as pf:
|
||||
js = json.load(pf)
|
||||
cam_loc = js['camera_location']
|
||||
cam_rot = js['camera_rotation_final']
|
||||
newname = posefile[:posefile.index('.')]
|
||||
fout.write("%f %f %f %f %f %f %s\n" %(cam_loc[0], cam_loc[1], cam_loc[2], cam_rot[0], cam_rot[1], cam_rot[2], newname))
|
||||
|
||||
fout.close()
|
|
@ -1 +0,0 @@
|
|||
nvcc -Wno-deprecated-gpu-targets -Xcompiler -fPIC -shared -o render_cuda_f.so render_cuda_filter.cu
|
|
@ -1,580 +0,0 @@
|
|||
#include <cstdlib>
|
||||
#include <cstdio>
|
||||
#include <vector>
|
||||
#include <algorithm>
|
||||
#include <math.h>
|
||||
#include <omp.h>
|
||||
#include <cuda.h>
|
||||
#include <cuda_runtime_api.h>
|
||||
|
||||
using namespace std;
|
||||
|
||||
const int TILE_DIM = 32;
|
||||
const int BLOCK_ROWS = 8;
|
||||
|
||||
#ifndef max
|
||||
|
||||
#define max( a, b ) ( ((a) > (b)) ? (a) : (b) )
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
#ifndef min
|
||||
|
||||
#define min( a, b ) ( ((a) < (b)) ? (a) : (b) )
|
||||
|
||||
#endif
|
||||
|
||||
//const bool pano = false;
|
||||
|
||||
__global__ void copy_mem(unsigned char *source, unsigned char *render)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int width = gridDim.x * TILE_DIM;
|
||||
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS)
|
||||
for (int channel = 0; channel < 3; channel ++ )
|
||||
render[3*((y+j)*width + x) + channel] = source[3 * ((y+j)*width + x) + channel];
|
||||
}
|
||||
|
||||
|
||||
__global__ void set_depth(unsigned int *depth)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int width = gridDim.x * TILE_DIM;
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS)
|
||||
depth[(y+j)*width + x] = 65535;
|
||||
}
|
||||
|
||||
|
||||
__global__ void char_to_int(int * img2, unsigned char * img)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int width = gridDim.x * TILE_DIM;
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS)
|
||||
img2[(y+j)*width + x] = img[3*((y+j)*width + x) + 0] * 256 * 256 + img[3*((y+j)*width + x) + 1] * 256 + img[3*((y+j)*width + x) + 2];
|
||||
}
|
||||
|
||||
|
||||
__global__ void int_to_char(int * img2, unsigned char * img)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int width = gridDim.x * TILE_DIM;
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS) {
|
||||
img[3*((y+j)*width + x)] = img2[(y+j)*width + x] / (256*256);
|
||||
img[3*((y+j)*width + x)+1] = img2[(y+j)*width + x] / 256 % 256;
|
||||
img[3*((y+j)*width + x)+2] = img2[(y+j)*width + x] % 256;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
__global__ void fill(unsigned char * img)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int width = gridDim.x * TILE_DIM;
|
||||
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS) {
|
||||
|
||||
if ( img[3*((y+j)*width + x)] + img[3*((y+j)*width + x)+1] + img[3*((y+j)*width + x)+2] == 0) {
|
||||
|
||||
img[3*((y+j)*width + x)] = img[3*((y+j)*width + x + 1)];
|
||||
img[3*((y+j)*width + x)+1] = img[3*((y+j)*width + x + 1)+1];
|
||||
img[3*((y+j)*width + x)+2] = img[3*((y+j)*width + x + 1)+2];
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
__global__ void selection_sum_weights(float * selection_sum, float * selection, int n, int stride) {
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int width = gridDim.x * TILE_DIM;
|
||||
int idx = 0;
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS) {
|
||||
selection_sum[((y+j)*width + x)] = 0;
|
||||
for ( idx = 0; idx < n; idx ++) {
|
||||
atomicAdd(&(selection_sum[((y+j)*width + x)]), selection[idx * stride + ((y+j)*width + x)]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
__global__ void merge(unsigned char * img_all, unsigned char * img, float * selection, int n, int stride)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int width = gridDim.x * TILE_DIM;
|
||||
int idx = 0;
|
||||
float sum = 0;
|
||||
float weight = 0;
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS) {
|
||||
sum = 0;
|
||||
for (idx = 0; idx < n; idx ++) sum += selection[idx * stride + ((y+j)*width + x)];
|
||||
|
||||
for (idx = 0; idx < n; idx ++) selection[idx * stride + ((y+j)*width + x)] /= (sum + 1e-5);
|
||||
|
||||
img[3*((y+j)*width + x)] = 0;
|
||||
img[3*((y+j)*width + x)+1] = 0;
|
||||
img[3*((y+j)*width + x)+2] = 0;
|
||||
|
||||
for (idx = 0; idx < n; idx ++) {
|
||||
|
||||
//weight = selection[idx * stride + ((y+j)*width + x)];
|
||||
weight = 0.25;
|
||||
//weight = 0.5;
|
||||
|
||||
|
||||
img[3*((y+j)*width + x)] += (unsigned char) (img_all[idx * stride * 3 + 3*((y+j)*width + x)] * weight);
|
||||
img[3*((y+j)*width + x)+1] += (unsigned char) (img_all[idx * stride * 3 + 3*((y+j)*width + x) + 1] * weight);
|
||||
img[3*((y+j)*width + x)+2] += (unsigned char)(img_all[idx * stride * 3 + 3*((y+j)*width + x) + 2] * weight);
|
||||
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
__global__ void merge_sum(unsigned char * img_all, unsigned char * img, float * selection, float * selection_sum, int n, int stride)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int width = gridDim.x * TILE_DIM;
|
||||
int idx = 0;
|
||||
float weight = 0;
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS) {
|
||||
|
||||
img[3*((y+j)*width + x)] = 0;
|
||||
img[3*((y+j)*width + x)+1] = 0;
|
||||
img[3*((y+j)*width + x)+2] = 0;
|
||||
|
||||
for (idx = 0; idx < n; idx ++) {
|
||||
|
||||
weight = selection[idx * stride + ((y+j)*width + x)] / selection_sum[((y+j)*width + x)];
|
||||
//weight = 0.25;
|
||||
//weight = 0.5;
|
||||
|
||||
|
||||
img[3*((y+j)*width + x)] += (unsigned char) (img_all[idx * stride * 3 + 3*((y+j)*width + x)] * weight);
|
||||
img[3*((y+j)*width + x)+1] += (unsigned char) (img_all[idx * stride * 3 + 3*((y+j)*width + x) + 1] * weight);
|
||||
img[3*((y+j)*width + x)+2] += (unsigned char)(img_all[idx * stride * 3 + 3*((y+j)*width + x) + 2] * weight);
|
||||
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
__global__ void to3d_point(float *depth, float *points3d)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int w = gridDim.x * TILE_DIM;
|
||||
int h = w / 2;
|
||||
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS)
|
||||
{
|
||||
|
||||
int iw = x;
|
||||
int ih = y + j;
|
||||
float depth_point = depth[ ih*w + iw ] * 128.0;
|
||||
float phi = ((float)(ih) + 0.5) / float(h) * M_PI;
|
||||
float theta = ((float)(iw) + 0.5) / float(w) * 2 * M_PI + M_PI;
|
||||
|
||||
points3d[(ih * w + iw) * 4 + 0] = depth_point * sin(phi) * cos(theta);
|
||||
points3d[(ih * w + iw) * 4 + 1] = depth_point * sin(phi) * sin(theta);
|
||||
points3d[(ih * w + iw) * 4 + 2] = depth_point * cos(phi);
|
||||
points3d[(ih * w + iw) * 4 + 3] = 1;
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
__global__ void transform(float *points3d_after, float *points3d, float * transformation_matrix)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int w = gridDim.x * TILE_DIM;
|
||||
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS)
|
||||
{
|
||||
int iw = x;
|
||||
int ih = y + j;
|
||||
for (int ic = 0; ic < 3; ic ++) {
|
||||
points3d_after[(ih * w + iw) * 3 + ic] = points3d[(ih * w + iw) * 4 + 0] * transformation_matrix[4 * ic + 0]
|
||||
+ points3d[(ih * w + iw) * 4 + 1] * transformation_matrix[4 * ic + 1]
|
||||
+ points3d[(ih * w + iw) * 4 + 2] * transformation_matrix[4 * ic + 2]
|
||||
+ points3d[(ih * w + iw) * 4 + 3] * transformation_matrix[4 * ic + 3];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//#define FOV_SCALE 1.73205080757
|
||||
//#define FOV_SCALE 1
|
||||
|
||||
|
||||
__global__ void transform2d(float *points3d_after, float fov_scale)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int w = gridDim.x * TILE_DIM;
|
||||
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS)
|
||||
{
|
||||
int iw = x;
|
||||
int ih = y + j;
|
||||
float x = points3d_after[(ih * w + iw) * 3 + 0];
|
||||
float y = points3d_after[(ih * w + iw) * 3 + 1];
|
||||
float z = points3d_after[(ih * w + iw) * 3 + 2];
|
||||
|
||||
points3d_after[(ih * w + iw) * 3 + 0] = x;//sqrt(x * x + y * y + z * z);
|
||||
//points3d_after[(ih * w + iw) * 3 + 1] = atan2(y, x);
|
||||
//points3d_after[(ih * w + iw) * 3 + 2] = atan2(sqrt(x * x + y * y), z);
|
||||
|
||||
float x2 = fov_scale * x;
|
||||
if ((x2 > 0) && (y < x2 * 1.1) && (y > -x2 * 1.1) && (z < x2 * 1.1) && (z > -x2 * 1.1)) {
|
||||
points3d_after[(ih * w + iw) * 3 + 1] = y / (x2 + 1e-5);
|
||||
points3d_after[(ih * w + iw) * 3 + 2] = -z / (x2 + 1e-5);
|
||||
}
|
||||
else {
|
||||
points3d_after[(ih * w + iw) * 3 + 1] = -1;
|
||||
points3d_after[(ih * w + iw) * 3 + 2] = -1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
__global__ void render_depth(float *points3d_polar, unsigned int * depth_render)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int w = gridDim.x * TILE_DIM;
|
||||
int h = w /2;
|
||||
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS)
|
||||
{
|
||||
int iw = x;
|
||||
int ih = y + j;
|
||||
int tx = round((points3d_polar[(ih * w + iw) * 3 + 1] + M_PI)/(2*M_PI) * w - 0.5);
|
||||
int ty = round((points3d_polar[(ih * w + iw) * 3 + 2])/M_PI * h - 0.5);
|
||||
int this_depth = (int)(512 * points3d_polar[(ih * w + iw) * 3 + 0]);
|
||||
atomicMin(&depth_render[(ty * w + tx)] , this_depth);
|
||||
}
|
||||
}
|
||||
|
||||
__global__ void get_average(unsigned char * img, int * nz, int * average, int scale)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int width = gridDim.x * TILE_DIM;
|
||||
//int h = width /2;
|
||||
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS)
|
||||
{
|
||||
int iw = x;
|
||||
int ih = y + j;
|
||||
|
||||
if (img[3*(ih*width + iw)] + img[3*(ih*width + iw)+1] + img[3*(ih*width + iw)+2] > 0)
|
||||
{
|
||||
//nz[ih/3 * width + iw/3] += 1;
|
||||
//average[3*(ih/3*width + iw/3)] += (int)img[3*(ih*width + iw)];
|
||||
//average[3*(ih/3*width + iw/3)+1] += (int)img[3*(ih*width + iw)+1];
|
||||
//average[3*(ih/3*width + iw/3)+2] += (int)img[3*(ih*width + iw)+2];
|
||||
|
||||
atomicAdd(&(nz[ih/scale * width + iw/scale]), 1);
|
||||
atomicAdd(&(average[3*(ih/scale*width + iw/scale)]), (int)img[3*(ih*width + iw)]);
|
||||
atomicAdd(&(average[3*(ih/scale*width + iw/scale)+1]), (int)img[3*(ih*width + iw)+1]);
|
||||
atomicAdd(&(average[3*(ih/scale*width + iw/scale)+2]), (int)img[3*(ih*width + iw)+2]);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
__global__ void fill_with_average(unsigned char *img, int * nz, int * average, int scale)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int width = gridDim.x * TILE_DIM;
|
||||
//int h = width /2;
|
||||
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS)
|
||||
{
|
||||
int iw = x;
|
||||
int ih = y + j;
|
||||
|
||||
if ((img[3*(ih*width + iw)] + img[3*(ih*width + iw)+1] + img[3*(ih*width + iw)+2] == 0) && (nz[ih/scale * width + iw/scale] > 0))
|
||||
{
|
||||
img[3*(ih*width + iw)] = (unsigned char)(average[3*(ih/scale*width + iw/scale)] / nz[ih/scale * width + iw/scale]);
|
||||
img[3*(ih*width + iw) + 1] = (unsigned char)(average[3*(ih/scale*width + iw/scale) + 1] / nz[ih/scale * width + iw/scale]);
|
||||
img[3*(ih*width + iw) + 2] = (unsigned char)(average[3*(ih/scale*width + iw/scale) + 2] / nz[ih/scale * width + iw/scale]);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
__global__ void render_final(float *points3d_polar, float * selection, float * depth_render, int * img, int * render, int oh, int ow)
|
||||
{
|
||||
int x = blockIdx.x * TILE_DIM + threadIdx.x;
|
||||
int y = blockIdx.y * TILE_DIM + threadIdx.y;
|
||||
int w = gridDim.x * TILE_DIM;
|
||||
int h = w /2;
|
||||
int maxsize = oh * ow;
|
||||
|
||||
for (int j = 0; j < TILE_DIM; j+= BLOCK_ROWS)
|
||||
{
|
||||
|
||||
int iw = x;
|
||||
int ih = y + j;
|
||||
|
||||
|
||||
int tx = round((points3d_polar[(ih * w + iw) * 3 + 1] + 1)/2 * ow - 0.5);
|
||||
int ty = round((points3d_polar[(ih * w + iw) * 3 + 2] + 1)/2 * oh - 0.5);
|
||||
|
||||
float tx_offset = ((points3d_polar[(ih * w + iw) * 3 + 1] + 1)/2 * ow - 0.5);
|
||||
float ty_offset = ((points3d_polar[(ih * w + iw) * 3 + 2] + 1)/2 * oh - 0.5);
|
||||
|
||||
float tx00 = 0;
|
||||
float ty00 = 0;
|
||||
|
||||
float tx01 = ((points3d_polar[(ih * w + iw + 1) * 3 + 1] + 1)/2 * ow - 0.5) - tx_offset;
|
||||
float ty01 = ((points3d_polar[(ih * w + iw + 1) * 3 + 2] + 1)/2 * oh - 0.5) - ty_offset;
|
||||
|
||||
float tx10 = ((points3d_polar[((ih + 1) * w + iw) * 3 + 1] + 1)/2 * ow - 0.5) - tx_offset;
|
||||
float ty10 = ((points3d_polar[((ih + 1) * w + iw) * 3 + 2] + 1)/2 * oh - 0.5) - ty_offset;
|
||||
|
||||
float tx11 = ((points3d_polar[((ih+1) * w + iw + 1) * 3 + 1] + 1)/2 * ow - 0.5) - tx_offset;
|
||||
float ty11 = ((points3d_polar[((ih+1) * w + iw + 1) * 3 + 2] + 1)/2 * oh - 0.5) - ty_offset;
|
||||
|
||||
float t00 = 0 * (float)tx00 + (float)tx01 * -1.0/3 + (float)tx10 * 2.0/3 + (float)tx11 * 1.0/3;
|
||||
float t01 = 0 * (float)ty00 + (float)ty01 * -1.0/3 + (float)ty10 * 2.0/3 + (float)ty11 * 1.0/3;
|
||||
float t10 = 0 * (float)tx00 + (float)tx01 * 2.0/3 + (float)tx10 * -1.0/3 + (float)tx11 * 1.0/3;
|
||||
float t11 = 0 * (float)ty00 + (float)ty01 * 2.0/3 + (float)ty10 * -1.0/3 + (float)ty11 * 1.0/3;
|
||||
|
||||
float det = t00 * t11 - t01 * t10 + 1e-10;
|
||||
|
||||
//printf("%f %f %f %f %f\n", t00, t01, t10, t11, det);
|
||||
|
||||
float it00, it01, it10, it11;
|
||||
|
||||
it00 = t11/det;
|
||||
it01 = -t01/det;
|
||||
it10 = -t10/det;
|
||||
it11 = t00/det;
|
||||
|
||||
//printf("inverse %f %f %f %f\n", it00, it01, it10, it11);
|
||||
|
||||
int this_depth = (int)(12800/128 * points3d_polar[(ih * w + iw) * 3 + 0]);
|
||||
int delta00 = (int)(12800/128 * points3d_polar[(ih * w + iw) * 3 + 0]) - (int)(100 * depth_render[(ty * ow + tx)]);
|
||||
int delta01 = (int)(12800/128 * points3d_polar[(ih * w + iw + 1) * 3 + 0]) - (int)(100 * depth_render[(ty * ow + tx + 1)]);
|
||||
int delta10 = (int)(12800/128 * points3d_polar[((ih + 1) * w + iw) * 3 + 0]) - (int)(100 * depth_render[((ty+1) * ow + tx)]);
|
||||
int delta11 = (int)(12800/128 * points3d_polar[((ih+1) * w + iw + 1) * 3 + 0]) - (int)(100 * depth_render[((ty+1) * ow + tx + 1)]);
|
||||
|
||||
int mindelta = min(min(delta00, delta01), min(delta10, delta11));
|
||||
int maxdelta = max(max(delta00, delta01), max(delta10, delta11));
|
||||
|
||||
int depth00 = (int)(12800/128 * points3d_polar[(ih * w + iw) * 3 + 0]);
|
||||
int depth01 = (int)(12800/128 * points3d_polar[(ih * w + iw + 1) * 3 + 0]);
|
||||
int depth10 = (int)(12800/128 * points3d_polar[((ih+1) * w + iw) * 3 + 0]);
|
||||
int depth11 = (int)(12800/128 * points3d_polar[((ih+1) * w + iw+1) * 3 + 0]);
|
||||
int max_depth = max(max(depth00, depth10), max(depth01, depth11));
|
||||
int min_depth = min(min(depth00, depth10), min(depth01, depth11));
|
||||
int delta_depth = max_depth - min_depth;
|
||||
|
||||
int txmin = floor(tx_offset + min(min(tx00, tx11), min(tx01, tx10)));
|
||||
int txmax = ceil(tx_offset + max(max(tx00, tx11), max(tx01, tx10)));
|
||||
int tymin = floor(ty_offset + min(min(ty00, ty11), min(ty01, ty10)));
|
||||
int tymax = ceil(ty_offset + max(max(ty00, ty11), max(ty01, ty10)));
|
||||
|
||||
float newx, newy;
|
||||
int r,g,b;
|
||||
int itx, ity;
|
||||
|
||||
//render[(ty * ow + tx)] = img[ih * w + iw];
|
||||
//selection[(ty * ow + tx)] = 1.0;
|
||||
|
||||
float tolerance = 0.1 * this_depth > 10? 0.1 * this_depth : 10;
|
||||
float tolerance2 = 0.05 * max_depth > 10? 0.05 * max_depth: 10;
|
||||
|
||||
float flank = 0.01;
|
||||
if ((delta_depth < tolerance2) && (y > 1 * h/8) && (y < (h*7)/8))
|
||||
if (((mindelta > - tolerance) && (maxdelta < tolerance)) && (this_depth < 10000)) {
|
||||
if (((txmax - txmin) * (tymax - tymin) < 1600) && (txmax - txmin < 40) && (tymax - tymin < 40))
|
||||
{
|
||||
for (itx = txmin; itx < txmax; itx ++)
|
||||
for (ity = tymin; ity < tymax; ity ++)
|
||||
{ if (( 0 <= itx) && (itx < ow) && ( 0 <= ity) && (ity < oh))
|
||||
{
|
||||
newx = (itx - tx_offset) * it00 + it10 * (ity - ty_offset);
|
||||
newy = (itx - tx_offset) * it01 + it11 * (ity - ty_offset);
|
||||
|
||||
//printf("%f %f\n", newx, newy);
|
||||
if ((newx > -flank) && (newx < 1 + flank) && (newy > -flank) && (newy < 1 + flank))
|
||||
{
|
||||
if (newx < 0) newx = 0;
|
||||
if (newy < 0) newy = 0;
|
||||
if (newx > 1) newx = 1;
|
||||
if (newy > 1) newy = 1;
|
||||
|
||||
r = img[(ih * w + iw)] / (256*256) * (1-newx) * (1-newy) + img[(ih * w + iw + 1)] / (256*256) * (1-newx) * (newy) + img[((ih+1) * w + iw)] / (256*256) * (newx) * (1-newy) + img[((ih+1) * w + iw + 1)] / (256*256) * newx * newy;
|
||||
g = img[(ih * w + iw)] / 256 % 256 * (1-newx) * (1-newy) + img[(ih * w + iw + 1)] / 256 % 256 * (1-newx) * (newy) + img[((ih+1) * w + iw)] / 256 % 256 * (newx) * (1-newy) + img[((ih+1) * w + iw + 1)] / 256 % 256 * newx * newy;
|
||||
b = img[(ih * w + iw)] % 256 * (1-newx) * (1-newy) + img[(ih * w + iw + 1)] % 256 * (1-newx) * (newy) + img[((ih+1) * w + iw)] % 256 * (newx) * (1-newy) + img[((ih+1) * w + iw + 1)] % 256 * newx * newy ;
|
||||
|
||||
if (r > 255) r = 255;
|
||||
if (g > 255) g = 255;
|
||||
if (b > 255) b = 255;
|
||||
|
||||
if ((ity * ow + itx > 0) && (ity * ow + itx < maxsize)) {
|
||||
render[(ity * ow + itx)] = r * 256 * 256 + g * 256 + b;
|
||||
selection[(ity * ow + itx)] = 1.0 / abs(det);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
extern "C"{
|
||||
|
||||
void render(int n, int h,int w, int oh, int ow, unsigned char * img, float * depth,float * pose, unsigned char * render, float * depth_render, float fov){
|
||||
//int ih, iw, i, ic;
|
||||
//printf("inside cuda code %d\n", depth);
|
||||
|
||||
//printf("scale %d\n", s);
|
||||
const int nx = w;
|
||||
const int ny = h;
|
||||
|
||||
const int onx = ow;
|
||||
const int ony = oh;
|
||||
|
||||
const size_t input_mem_size = nx*ny;
|
||||
const size_t output_mem_size = onx * ony;
|
||||
|
||||
dim3 dimGrid(nx/TILE_DIM, ny/TILE_DIM, 1);
|
||||
dim3 dimGrid_out(onx/TILE_DIM, ony/TILE_DIM, 1);
|
||||
dim3 dimBlock(TILE_DIM, BLOCK_ROWS, 1);
|
||||
|
||||
unsigned char *d_img, *d_render, *d_render_all;
|
||||
float *d_depth, *d_pose;
|
||||
float *d_depth_render;
|
||||
float *d_3dpoint, *d_3dpoint_after;
|
||||
|
||||
float * d_selection, * d_selection_sum;
|
||||
int * nz;
|
||||
int * average;
|
||||
|
||||
int *d_render2, *d_img2;
|
||||
|
||||
cudaMalloc((void **)&d_img, input_mem_size * sizeof(unsigned char) * 3);
|
||||
cudaMalloc((void **)&d_img2, input_mem_size * sizeof(int));
|
||||
cudaMalloc((void **)&d_render, output_mem_size * sizeof(unsigned char) * 3);
|
||||
cudaMalloc((void **)&d_render_all, output_mem_size * sizeof(unsigned char) * 3 * n);
|
||||
cudaMalloc((void **)&d_depth, input_mem_size * sizeof(float));
|
||||
cudaMalloc((void **)&d_depth_render, output_mem_size * sizeof(float));
|
||||
cudaMalloc((void **)&d_3dpoint, input_mem_size * sizeof(float) * 4);
|
||||
cudaMalloc((void **)&d_3dpoint_after, input_mem_size * sizeof(float) * 4);
|
||||
cudaMalloc((void **)&d_pose, sizeof(float) * 16);
|
||||
|
||||
|
||||
cudaMalloc((void **)&d_selection, output_mem_size * sizeof(float) * n);
|
||||
cudaMalloc((void **)&d_selection_sum, output_mem_size * sizeof(float));
|
||||
|
||||
cudaMalloc((void **)&d_render2, output_mem_size * sizeof(int));
|
||||
|
||||
|
||||
cudaMalloc((void **)&nz, output_mem_size * sizeof(int));
|
||||
cudaMalloc((void **)&average, output_mem_size * sizeof(int) * 3);
|
||||
|
||||
|
||||
cudaMemset(nz, 0, output_mem_size * sizeof(int));
|
||||
cudaMemset(average, 0, output_mem_size * sizeof(int) * 3);
|
||||
cudaMemset(d_selection, 0, output_mem_size * sizeof(float) * n);
|
||||
cudaMemset(d_selection_sum, 0, output_mem_size * sizeof(float));
|
||||
|
||||
cudaMemcpy(d_depth_render, depth_render, output_mem_size * sizeof(float), cudaMemcpyHostToDevice);
|
||||
cudaMemset(d_render_all, 0, output_mem_size * sizeof(unsigned char) * 3 * n);
|
||||
|
||||
int idx;
|
||||
for (idx = 0; idx < n; idx ++) {
|
||||
|
||||
cudaMemcpy(d_pose, &(pose[idx * 16]), sizeof(float) * 16, cudaMemcpyHostToDevice);
|
||||
cudaMemcpy(d_img, &(img[idx * input_mem_size * 3]), input_mem_size * sizeof(unsigned char) * 3, cudaMemcpyHostToDevice);
|
||||
cudaMemcpy(d_depth, &(depth[idx * input_mem_size]), input_mem_size * sizeof(float), cudaMemcpyHostToDevice);
|
||||
|
||||
cudaMemset(d_render, 0, output_mem_size * sizeof(unsigned char) * 3);
|
||||
cudaMemset(d_render2, 0, output_mem_size * sizeof(int));
|
||||
|
||||
cudaMemset(d_img2, 0, input_mem_size * sizeof(int));
|
||||
cudaMemset(d_3dpoint, 0, input_mem_size * sizeof(float) * 4);
|
||||
cudaMemset(d_3dpoint_after, 0, input_mem_size * sizeof(float) * 3);
|
||||
|
||||
to3d_point<<< dimGrid, dimBlock >>>(d_depth, d_3dpoint);
|
||||
transform<<< dimGrid, dimBlock >>>(d_3dpoint_after, d_3dpoint, d_pose);
|
||||
|
||||
float fov_scale = tan(fov/2);
|
||||
|
||||
transform2d<<<dimGrid, dimBlock>>>(d_3dpoint_after, fov_scale);
|
||||
|
||||
char_to_int <<< dimGrid, dimBlock >>> (d_img2, d_img);
|
||||
|
||||
render_final <<< dimGrid, dimBlock >>> (d_3dpoint_after, &(d_selection[idx * onx * ony]), d_depth_render, d_img2, d_render2, oh, ow);
|
||||
|
||||
//int_to_char <<< dimGrid_out, dimBlock >>> (d_render2, d_render);
|
||||
int_to_char <<< dimGrid_out, dimBlock >>> (d_render2, &(d_render_all[idx * output_mem_size * 3]));
|
||||
|
||||
|
||||
int fill_size[1] = {3};
|
||||
|
||||
for (int j = 0; j < 1; j++) {
|
||||
cudaMemset(nz, 0, output_mem_size * sizeof(int));
|
||||
cudaMemset(average, 0, output_mem_size * sizeof(int) * 3);
|
||||
get_average <<< dimGrid_out, dimBlock >>> (&(d_render_all[idx * output_mem_size * 3]), nz, average, fill_size[j]);
|
||||
fill_with_average <<< dimGrid_out, dimBlock >>> (&(d_render_all[idx * output_mem_size * 3]), nz, average, fill_size[j]);
|
||||
}
|
||||
}
|
||||
|
||||
selection_sum_weights <<< dimGrid_out, dimBlock >>> (d_selection_sum, d_selection, n, output_mem_size);
|
||||
merge_sum <<< dimGrid_out, dimBlock >>> (d_render_all, d_render, d_selection, d_selection_sum, n, output_mem_size);
|
||||
//merge <<< dimGrid_out, dimBlock >>> (d_render_all, d_render, d_selection, n, output_mem_size);
|
||||
|
||||
cudaMemcpy(render, d_render, output_mem_size * sizeof(unsigned char) * 3 , cudaMemcpyDeviceToHost);
|
||||
|
||||
|
||||
cudaFree(d_img);
|
||||
cudaFree(d_depth);
|
||||
cudaFree(d_render2);
|
||||
cudaFree(d_img2);
|
||||
cudaFree(d_render);
|
||||
cudaFree(d_depth_render);
|
||||
cudaFree(d_3dpoint);
|
||||
cudaFree(d_3dpoint_after);
|
||||
cudaFree(d_pose);
|
||||
cudaFree(d_render_all);
|
||||
cudaFree(d_selection);
|
||||
cudaFree(nz);
|
||||
cudaFree(average);
|
||||
cudaFree(d_selection_sum);
|
||||
}
|
||||
|
||||
|
||||
}//extern "C"
|
11
setup.py
11
setup.py
|
@ -14,10 +14,8 @@ class PostInstallCommand(install):
|
|||
install.run(self)
|
||||
'''
|
||||
|
||||
setup(name='gibson',
|
||||
version='0.3.1',
|
||||
description='Real Environment Developed by Stanford University',
|
||||
url='https://github.com/fxia22/realenv',
|
||||
setup(name='gibson2',
|
||||
version='0.0.1',
|
||||
author='Stanford University',
|
||||
zip_safe=False,
|
||||
install_requires=[
|
||||
|
@ -41,10 +39,5 @@ setup(name='gibson',
|
|||
'aenum'
|
||||
],
|
||||
tests_require=[],
|
||||
# cmdclass={
|
||||
# 'install': PostInstallCommand
|
||||
#}
|
||||
)
|
||||
|
||||
|
||||
# check_call("bash realenv/envs/build.sh".split())
|
||||
|
|
Loading…
Reference in New Issue