Initial commit

This commit is contained in:
Martin Felis
2021-11-11 21:22:24 +01:00
commit b78045ffe7
812 changed files with 421882 additions and 0 deletions
+4
View File
@@ -0,0 +1,4 @@
---
BasedOnStyle: Google
...
+3
View File
@@ -0,0 +1,3 @@
build/
build-cc/
.DS_Store
+8
View File
@@ -0,0 +1,8 @@
# Default ignored files
/shelf/
/workspace.xml
# Editor-based HTTP Client requests
/httpRequests/
# Datasource local storage ignored files
/dataSources/
/dataSources.local.xml
+1
View File
@@ -0,0 +1 @@
ozz
+4
View File
@@ -0,0 +1,4 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="CMakeWorkspace" PROJECT_DIR="$PROJECT_DIR$" />
</project>
+8
View File
@@ -0,0 +1,8 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="ProjectModuleManager">
<modules>
<module fileurl="file://$PROJECT_DIR$/.idea/ozz-animation.iml" filepath="$PROJECT_DIR$/.idea/ozz-animation.iml" />
</modules>
</component>
</project>
+2
View File
@@ -0,0 +1,2 @@
<?xml version="1.0" encoding="UTF-8"?>
<module classpath="CMake" type="CPP_MODULE" version="4" />
+6
View File
@@ -0,0 +1,6 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="VcsDirectoryMappings">
<mapping directory="$PROJECT_DIR$" vcs="Git" />
</component>
</project>
+387
View File
@@ -0,0 +1,387 @@
language: cpp
dist: xenial
jobs:
include:
# Emscripten cross compiling
#- os: linux
# compiler: gcc
# env:
# - env_build_emscripten=1
# mac os
# Default mac os clang build
- os: osx
osx_image: xcode10
compiler: clang
- os: osx
compiler: clang
- os: osx
compiler: clang
env:
- env_cmake_configuration=Release
# Xcode mac os clang build
- os: osx
compiler: clang
env :
- env_cmake_generator=Xcode
- os: osx
compiler: clang
env :
- env_cmake_generator=Xcode
- env_cmake_configuration=Release
# Linux ARM
- os: linux
compiler: clang
env:
- env_build_fbx=0
- env_cmake_configuration=Debug
arch:
- arm64
- os: linux
compiler: clang
env:
- env_build_fbx=0
- env_cmake_configuration=Release
arch:
- arm64
# Linux
# Default linux clang debug
- os: linux
compiler: clang
env:
- env_cmake_configuration=Debug
# Default linux release clang
- os: linux
compiler: clang
env:
- env_cmake_configuration=Release
# Specific configurations
- os: linux
compiler: clang
env:
- env_build_fbx=0
- os: linux
compiler: clang
env:
- env_build_gltf=0
- os: linux
compiler: clang
env:
- env_build_howtos=0
- os: linux
compiler: clang
env:
- env_build_samples=0
- os: linux
compiler: clang
env:
- env_build_tools=0
- os: linux
compiler: clang
env:
- env_build_postfix=0
- os: linux
compiler: clang
env:
- env_build_simd_ref=1
- os: linux
compiler: clang
env:
- env_build_tests=0
- os: linux
compiler: clang
env:
- env_build_fbx=0
- env_build_gltf=0
- env_build_samples=0
- os: linux
compiler: clang
env:
- env_build_fbx=0
- env_build_gltf=0
- env_build_tests=0
- os: linux
compiler: clang
env:
- env_build_data=0
- env_build_fbx=0
- env_build_gltf=0
- env_build_samples=0
- env_build_tests=0
- os: linux
compiler: clang
env:
- env_build_data=0
- os: linux
compiler: clang
env:
- env_src_root="../test/sub/"
# Default linux gcc debug
- os: linux
compiler: gcc
env:
- env_cmake_configuration=Debug
# Default linux gcc release
- os: linux
compiler: gcc
env:
- env_cmake_configuration=Release
# Newer gcc
- os: linux
compiler: gcc-4.9
env:
- env_cmake_cxx_compiler=g++-4.9
- env_cmake_c_compiler=gcc-4.9
addons:
apt:
sources:
- ubuntu-toolchain-r-test
packages:
- g++-4.9
- os: linux
compiler: gcc-5
env:
- env_cmake_cxx_compiler=g++-5
- env_cmake_c_compiler=gcc-5
addons:
apt:
sources:
- ubuntu-toolchain-r-test
packages:
- g++-5
- os: linux
compiler: gcc-6
env:
- env_cmake_cxx_compiler=g++-6
- env_cmake_c_compiler=gcc-6
addons:
apt:
sources:
- ubuntu-toolchain-r-test
packages:
- g++-6
- os: linux
compiler: gcc-7
env:
- env_cmake_cxx_compiler=g++-7
- env_cmake_c_compiler=gcc-7
addons:
apt:
sources:
- ubuntu-toolchain-r-test
packages:
- g++-7
- os: linux
compiler: gcc-8
env:
- env_cmake_cxx_compiler=g++-8
- env_cmake_c_compiler=gcc-8
addons:
apt:
sources:
- ubuntu-toolchain-r-test
packages:
- g++-8
# Newer clang
- os: linux
compiler: clang-3.9
env:
- env_cmake_cxx_compiler=clang++-3.9
- env_cmake_c_compiler=clang-3.9
addons:
apt:
sources:
- ubuntu-toolchain-r-test
- llvm-toolchain-xenial-3.9
packages:
- clang-3.9
- os: linux
compiler: clang-4.0
env:
- env_cmake_cxx_compiler=clang++-4.0
- env_cmake_c_compiler=clang-4.0
addons:
apt:
sources:
- ubuntu-toolchain-r-test
- llvm-toolchain-xenial-4.0
packages:
- clang-4.0
- os: linux
compiler: clang-5.0
env:
- env_cmake_cxx_compiler=clang++-5.0
- env_cmake_c_compiler=clang-5.0
addons:
apt:
sources:
- ubuntu-toolchain-r-test
- llvm-toolchain-xenial-5.0
packages:
- clang-5.0
- os: linux
compiler: clang-6.0
env:
- env_cmake_cxx_compiler=clang++-6.0
- env_cmake_c_compiler=clang-6.0
addons:
apt:
sources:
- ubuntu-toolchain-r-test
- llvm-toolchain-xenial-6.0
packages:
- clang-6.0
- os: linux
compiler: clang-7
env:
- env_cmake_cxx_compiler=clang++-7
- env_cmake_c_compiler=clang-7
addons:
apt:
sources:
- ubuntu-toolchain-r-test
- llvm-toolchain-xenial-7
packages:
- clang-7
- os: linux
compiler: clang-8
env:
- env_cmake_cxx_compiler=clang++-8
- env_cmake_c_compiler=clang-8
addons:
apt:
sources:
- ubuntu-toolchain-r-test
- llvm-toolchain-xenial-8
packages:
- clang-8
# older fbx sdk
- os: linux
compiler: gcc
env:
- fbx_download=http://download.autodesk.com/us/fbx/2017/2017.1/fbx20171_fbxsdk_linux.tar.gz
- os: osx
compiler: clang
env:
- fbx_download=http://download.autodesk.com/us/fbx/2017/2017.1/fbx20171_fbxsdk_clang_mac.pkg.tgz
before_install:
- echo before_install----------------------------------------------------------
install:
- echo install-----------------------------------------------------------------
# Download and install mesa dev
- if [[ $TRAVIS_OS_NAME == "linux" ]]; then
sudo apt-get install libgl1-mesa-dev libglu1-mesa-dev;
fi
# Download and install fbx sdk
# "|| true" because 2019 sdk would return code 130 when reading the readme
# chmod because fbx2019 will install with 700
- if [[ $TRAVIS_OS_NAME == "linux" ]]; then
if [ -z "$fbx_download" ]; then
FBX_DOWNLOAD=${fbx_download:-"http://www.autodesk.com/content/dam/autodesk/www/adn/fbx/20192/fbx20192_fbxsdk_linux.tar.gz"};
else
FBX_DOWNLOAD="$fbx_download";
fi;
mkdir fbx;
cd fbx;
sudo wget $FBX_DOWNLOAD -O fbx.tar.gz;
sudo tar -xf "fbx.tar.gz";
(yes yes | sudo ./*_fbxsdk_linux /usr/local) || true;
sudo chmod -R 755 /usr/local/lib;
sudo chmod -R 755 /usr/local/include;
cd ..;
fi
- if [[ $TRAVIS_OS_NAME == "osx" ]]; then
if [ -z "$fbx_download" ]; then
FBX_DOWNLOAD=${fbx_download:-"http://www.autodesk.com/content/dam/autodesk/www/adn/fbx/20192/fbx20192_fbxsdk_clang_mac.pkg.tgz"};
else
FBX_DOWNLOAD="$fbx_download";
fi;
mkdir fbx;
cd fbx;
sudo wget $FBX_DOWNLOAD -O fbx.tgz;
sudo tar -xf "fbx.tgz";
sudo installer -pkg *_fbxsdk_clang_macos.pkg -target /;
cd ..;
fi
# Download and install emscripten sdk
- if [[ $env_build_emscripten ]]; then
sudo apt-get install software-properties-common -y;
sudo add-apt-repository ppa:george-edison55/cmake-3.x -y;
sudo apt-get update;
sudo apt-get install --only-upgrade cmake -y;
git clone https://github.com/juj/emsdk.git;
cd emsdk;
sudo ./emsdk update-tags;
sudo ./emsdk install sdk-nightly-latest-64bit;
sudo ./emsdk activate --embedded sdk-nightly-latest-64bit;
source ./emsdk_env.sh;
cd ..;
fi
before_script:
- echo before_script-----------------------------------------------------------
# Setup default environment variables
- if [[ -z $env_src_root ]]; then export env_src_root=".."; fi
- if [[ -z $env_build_fbx ]]; then export env_build_fbx=1; fi
- if [[ -z $env_build_gltf ]]; then export env_build_gltf=1; fi
- if [[ -z $env_build_data ]]; then export env_build_data=1; fi
- if [[ -z $env_build_howtos ]]; then export env_build_howtos=1; fi
- if [[ -z $env_build_tools ]]; then export env_build_tools=1; fi
- if [[ -z $env_build_postfix ]]; then export env_build_postfix=1; fi
- if [[ -z $env_build_samples ]]; then export env_build_samples=1; fi
- if [[ -z $env_build_simd_ref ]]; then export env_build_simd_ref=0; fi
- if [[ -z $env_build_tests ]]; then export env_build_tests=1; fi
- if [[ -z $env_cmake_configuration ]]; then export env_cmake_configuration=Debug; fi
- if [[ -z $env_cmake_cxx_compiler ]]; then export env_cmake_cxx_compiler=$CXX; fi
- if [[ -z $env_cmake_c_compiler ]]; then export env_cmake_c_compiler=$CC; fi
- if [[ -z $env_cmake_generator ]]; then export env_cmake_generator="Unix Makefiles"; fi
- if [[ $env_cmake_generator == "Unix Makefiles" ]]; then export env_cmake_generator_specific="-j2"; fi
- if [[ $env_cmake_generator == "Unix Makefiles" ]]; then export env_ctest_generator_specific="-j16"; fi
- if [[ $EMSCRIPTEN ]]; then env_cmake_toolchain="-DCMAKE_TOOLCHAIN_FILE=$EMSCRIPTEN/cmake/Modules/Platform/Emscripten.cmake"; fi
# Display cmake version
- cmake --version
script:
- echo script------------------------------------------------------------------
# Configure build
- mkdir build
- cd build
- echo $env_cmake_toolchain
- cmake -G "$env_cmake_generator" $env_cmake_toolchain -DCMAKE_CXX_COMPILER=$env_cmake_cxx_compiler -DCMAKE_C_COMPILER=$env_cmake_c_compiler -DCMAKE_BUILD_TYPE=$env_cmake_configuration -Dozz_build_fbx=$env_build_fbx -Dozz_build_data=$env_build_data -Dozz_build_howtos=$env_build_howtos -Dozz_build_samples=$env_build_samples -Dozz_build_postfix=$env_build_postfix -Dozz_build_tools=$env_build_tools -Dozz_build_simd_ref=$env_build_simd_ref -Dozz_build_tests=$env_build_tests $env_src_root
# Build
- cmake --build ./ --config $env_cmake_configuration --use-stderr -- $env_cmake_generator_specific
# Test
- ctest --build-config $env_cmake_configuration --output-on-failure -- $env_ctest_generator_specific
after_success:
- echo after_success-----------------------------------------------------------
after_failure:
- echo after_failure-----------------------------------------------------------
before_deploy:
#- echo before_deploy-----------------------------------------------------------
deploy:
#- echo deploy------------------------------------------------------------------
after_deploy:
#- echo after_deploy------------------------------------------------------------
after_script:
#- echo after_script------------------------------------------------------------
+12
View File
@@ -0,0 +1,12 @@
The following authors have all licensed their contributions to ozz-animation under the licensing terms detailed in [LICENSE.md](LICENSE.md):
- Guillaume Blanc <guillaumeblanc.sc@gmail.com> - Project's owner and main author.
- Tomasz Dąbrowski <t.dabrowski@rock-hard.eu>
- Jean-François Verdon <jf.verdon@mgdesign.fr>
- Kyrylo Bazhenov <bazhenovc@gmail.com>
- Tian Li <tian.li@monstar-lab-cn.com>
- Cloud Wu <cloudwu@gmail.com>
- Kyle Rocha <kyle@luminawesome.com>
- Andreas Streichardt <andreas.streichardt@gmail.com>
- Chen Junjie <kitchen.gz.020@gmail.com>
- James W. Walker <jw@jwwalker.com>
+335
View File
@@ -0,0 +1,335 @@
Release version 0.13.0
----------------------
* Tools
- [gltf2ozz] Command line tool utility to import animations and skeletons from glTF files. gltf2ozz can be configured via command line options and [json configuration files](src/animation/offline/tools/reference.json), in the exact same way as fbx2ozz.
- #91 Fixup animation name when used as an output filename (via json configuration wildcard option), so they comply with most os filename restrictions.
* Samples
- [skinning] Adds a new sample to explain skinning matrices setup.
* Build pipeline
- Enables c++11 feature by default for all targets.
* Library
- [animation] Removes skeleton_utils.h IterateMemFun helper that can be replaced by std::bind.
- [base] Removes ozz::memory::Allocator::Reallocate() function as it's rarely used and complex to overload.
- [base] Replaces OZZ_NEW and OZZ_DELETE macros with template functions ozz::New and ozz::Delete.
- [base] Removes ScopedPtr in favor of an alias to standard unique_ptr that remaps to ozz deallocator. Implements make_unique using ozz allocator.
- [base] Uses template aliasing (using keyword) to redirect ozz to std containers. This allows to get rid of ::Std when using ozz containers.
- [base] Renames all aliased ozz containers to their original std name: vector, map etc...
- [base] Renames ozz::Range to ozz::span, ozz::make_range to ozz::make_span to comply with std containers. Range count() and size() methods are renamed to size() and size_bytes() respectively, so this needs special attention to avoid mistakes.
- [base] Replaces OZZ_ALIGN_OF and OZZ_ALIGN by standard alignof and alignas keywords.
- [base] Replaces OZZ_STATIC_ASSERT by standard static_assert keyword.
Release version 0.12.1
----------------------
* Library
- [base] Fixes memory overwrite when reallocating a buffer of smaller size using ozz default memory allocator.
Release version 0.12.0
----------------------
* Library
- [offline] Simplified AnimationOptimizer settings to a single tolerance and distance. Tolerance is the maximum error that an optimization is allowed to generate on a whole joint hierarchy, while the other parameter is the distance (from the joint) at which error is measured. This second parameter allows to emulate effect on skinning or a long object (sword) attached to a joint (hand).
- [offline] Adds options to AnimationOptimizer to override optimization settings for a joint. This implicitly have an effect on the whole chain, up to that joint. This allows for example to have aggressive optimization for a whole skeleton, except for the chain that leads to the hand if user wants it to be precise.
- [offline] Switches AnimationOptimizer and TrackOptimizer to RamerDouglasPeucker decimation algorithm which delivers better precision than original one. It also ensures that first and last points are preserved, avoiding visual issues for looping animations.
- [offline] Changes order of parameters for IterateJointsDF so it's less error prone.
- [memory] Implements ScopedPtr smart pointer. ScopedPtr implementation guarantees the pointed object will be deleted, either on destruction of the ScopedPtr, or via an explicit reset / reassignation.
- [math] Quaternion compare function now takes cosine of half angle as argument, to avoid computing arc cosine for every comparison as the tolerance is usually constant.
- [base] Replaces ozz::memory::Allocator New and Delete function with OZZ_NEW and OZZ_DELETE macros, in order to provide an interface that supports any type and number of arguments (without requiring c++11).
- [base] #83 Allows user code to disable definition of global namespace sse \_m128 +-/* operators, as they might conflict with other sse math libraries.
* Samples
- [optimize] Exposes joint setting overriding option (from AnimationOptimizer) to sample gui. Displays median and maximum error values.
* Tools
- Moves keyframe reduction stage for additive animations before computing delta with reference pose. This ensures whole skeleton hierarchy is known before decimating keyframes.
Release version 0.11.0
----------------------
* Library
- [animation] Adds two-bone and aim inverse kinematic solvers. They can be used at runtime to procedurally affect joint local-space transforms.
- [animation] Allows resizing SamplingCache, meaning the can be allocated without knowing the number of joints the cache needs to support.
- [animation] Allow ozz::animation::LocalToModelJob to partially update a hierarchy, aka all children of a joint. This is useful when changes to a local-space pose has been limited to part of the joint hierarchy, like when applying IK or modifying model-space matrices independently from local-space transform.
- [animation] Changes ozz::animation::Skeleton joints from breadth-first to depth-first. This change breaks compatibility of previous ozz::animation::offline::RawAnimation, ozz::animation::Animation and ozz::animation::Skeleton archives.
- [animation] Renames track_triggering_job_stl.h to track_triggering_job_trait.h.
- [offline] #62 Adds an a way to specify additive animation reference pose to ozz::animation::offline::AdditiveAnimationBuilder.
- [memory] Removes (too error prone) ozz::memory::Allocator typed allocation functions.
- [math] Changes all conversion from AxisAngle to use separate arguments for axis and angle. This is more in line with function use cases.
- [math] Adds quaternions initialization from two vectors.
- [simd math] Updates simd math functions to prevent unnecessary operations. Some functions now return undefined values for some components, like Dot3 that will return the dot value in x and undefined values for x, y, z. See [simd_math.h](include/ozz/base/maths/simd_math.h) for each function documentation.
- [simd math] Implements AVX and FMA optimizations (when enabled at compile time).
- [simd math] Implements simd quaternions, making it easier and more efficient to use quaternion with other simd math code.
- [simd math] Exposes swizzling operations.
* Samples
- [two bone ik] Adds two-bone ik sample, showing how ozz::animation::IKTwoBoneJob can be used on a robot arm.
- [look at] Adds a look-at sample, using ozz::animation::IKAimJob on a chain of bones to distribute aiming contribution to more than a single joint.
- [foot_ik] Adds foot-ik sample, which corrects character legs and ankles procedurally at runtime, as well as character/pelvis height, so that the feet can touch and adapt to the ground.
* Build pipeline
- Adds support for fbx sdk 2019. This version is now mandatory for vs2017 builds.
- Adds support to macos 10.14 Mojave and Xcode 10.0.
* Tools
- Adds point and vector property types (used to import tracks). These two types are actually float3 types, with scene axis and unit conversion applied.
- Adds an option to importer tools to select additive animation reference pose.
* Build pipeline
- #40 Adds ozz_build_postfix option.
- #41 Adds ozz_build_tools option.
Release version 0.10.0
----------------------
* Library
- [animation] Adds user-channel feature #4. ozz now offers tracks of float, float2, float3, float4 and quaternion for both raw/offline and runtime. A track can be used to store animated user-data, aka data that aren't joint transformations. Runtime jobs allow to query a track value for any time t (ozz::animation::TrackSamplingJob), or to find all rising and falling edges that happened during a period of time (ozz::animation::TrackTriggeringJob). Utilities allow to optimize a raw track (ozz::animation::offline::TrackOptimizer) and build a runtime track (ozz::animation::offline::TrackOptimizer). fbx2ozz comes with the ability to import tracks from fbx node properties.
- [animation] Changed ozz::animation::SamplingJob::time (in interval [0,duration]) to a ratio (in unit interval [0,1]). This is a breaking change, aiming to unify sampling of animations and tracks. To conform with this change, sampling time should simply be divided by animation duration. ozz::sample:AnimationController has been updated accordingly. Offline animations and tools aren't impacted.
- [base] Changes non-intrusive serialization mechanism to use a specialize template struct "Extern" instead of function overloading.
* Tools
- Merged \*2skel and \*2anim in a single tool (\*2ozz, fbx2ozz for fbx importer) where all options are specified as a json config file. List of options with default values are available in [src/animation/offline/tools/reference.json](src/animation/offline/tools/reference.json) file. Consequently, ozz_animation_offline_skel_tools and ozz_animation_offline_anim_tools are also merged into a single ozz_animation_tools library.
- Adds options to import user-channel tracks (from node properties for fbx) using json "animations[].tracks[].properties[]" definition.
- Adds an option while importing skeletons to choose scene node types that must be considered as skeleton joints, ie not restricting to scene joints only. This is useful for the baked sample for example, which animates mesh nodes.
* Build pipeline
- ozz optionnaly supports c++11 compiler.
- Adds ozz_build_data option (OFF by default), to avoid building data on every code change. Building data takes time indeed, and isn't required on every change. It should be turned ON when output format changes to update all data again.
- Removes fused source files from the depot. Fused files are generated during build to ${PROJECT_BINARY_DIR}/src_fused/ folder. To generate fused source files without building the whole project, then build BUILD_FUSE_ALL target with "cmake --build . --target BUILD_FUSE_ALL" command.
- Adds support for Visual Studio 15 2017, drops Visual Studio 11 2012.
* Samples
- [user_channel] Adds new user-channel sample, demonstrating usage of user-channel tracks API and import pipeline usage.
- [sample_fbx2mesh] Remaps joint indices to the smaller range of skeleton joints that are actually used by the skinning. It's now required to index skeleton matrices using ozz::sample::framework:Mesh::joint_remaps when build skinning matrices.
- [multithread] Switched from OpenMP to c++11 std::async API to implement a parallel-for loop over all computation tasks.
Release version 0.9.1
---------------------
* Build pipeline
- Allows to use ozz-animation from another project using cmake add_subdirectory() command, conforming with [online documentation](http://guillaumeblanc.github.io/ozz-animation/documentation/build/).
- Adds Travis-CI (http://travis-ci.org/guillaumeblanc/ozz-animation) and AppVeyor (http://ci.appveyor.com/project/guillaumeblanc/ozz-animation) continuous integration support.
- Exposes MSVC /MD and /MT option (ozz_build_msvc_rt_dll). Default is /MD, same as MSVC/cmake.
- Adds support for Xcode 8.3.2 (fbx specific compilation option).
Release version 0.9.0
---------------------
* Library
- [offline] Removes dae2* tools, offline libraries and dependencies. Collada is still supported through fbx2* tools suite, as they are based on the Autodesk Fbx sdk.
- [offline][animation] Adds a name to the offline::RawAnimation and Animation data structure. ozz::animation::Animation serialization format has changed, animations generated with a previous version need to be re-built.
- [animation] Optimizes animation and skeleton allocation strategy, merging all member buffers to a single allocation.
- [animation] Fixes memory read overrun in ozz::animation::Skeleton while fixing up skeleton joint names.
- [offline] #5 Allows importing of all animations from a DCC file with a single command. fbx2anim now support the use of the wildcard character '*' in the --animation option (output file name), which is replaced with the imported animation names when the output file is written to disk.
- [offline] Uses scene frame rate as the default sampling rate option in fbx2anim. Allows to match DCC keys and avoid interpolation issues while importing from fbx sdk.
- [base] Adds support for Range serialization (as an array) via ozz::io::MakeArray utility.
- [base] Fixes SSE matrix decomposition implementation which wasn't able to decompose matrices with very small scales.
* Build pipeline
- Rework build pipeline and media directory to allow to have working samples even if Fbx sdk isn't available to build fbx tools. Media directory now contains pre-built binary data for samples usage.
- A Fused version of the sources for all libraries can be found in src_fused folder. It is automatically generated by cmake when any library source file changes.
- #20 FindFbx.cmake module now supports a version as argument which can be tested in conformance with cmake find_package specifications.
- Adds a clang-format target that re-formats all sdk sources. This target is not added to the ALL_BUILD target. It must be ran manually.
- Removes forced MSVC compiler options (SSE, RTC, GS) that are already properly handled by default.
* Samples
- [baked] Adds new baked physic sample. Demonstrates how to modify Fbx skeleton importer to build skeletons from custom nodes, and use an animation to drive rigid bodies.
- [sample_fbx2mesh] Fixes welding of redundant vertices. Re-imported meshes now have significantly less vertices.
- [sample_fbx2mesh] Adds UVs, tangents and vertex color to ozz::sample::framework::Mesh structure. Meshes generated with a previous version need to be re-built.
- [framework] Fixes sample first frame time, setting aside time spent initializing.
- [framework] Supports emscripten webgl canvas resizing.
Release version 0.8.0
---------------------
* Library
- [animation] Adds additive blending support to ozz::animation::BlendingJob. Animations used for additive blending should be delta animations (relative to the first frame). Use ozz::animation::offline::AdditiveAnimationBuilder to prepare such animations.
- [animation] Improves quaternion compression scheme by quantizing the 3 smallest components of the quaternion, instead of the firsts 3. This improves numerical accuracy when the restored component (4th) is small. It also allows to pre-multiply each of the 3 smallest components by sqrt(2), maximizing quantization range by over 41%.
- [offline] Improves animation optimizer process (ozz::animation::offline::AnimationOptimizer) with a new hierarchical translation tolerance. The optimizer now computes the error (a distance) generated from the optimization of a joint on its whole child hierarchy (like the whole arm length and hand when optimizing the shoulder). This provides a better optimization in both quality and quantity.
- [offline] Adds ozz::animation::offline::AdditiveAnimationBuilder utility to build delta animations that can be used for additive blending. This utility processes a raw animation to calculate the delta transformation from the first key to all subsequent ones, for all tracks.
- [offline] Adds --additive option to dae2anim and fbx2anim, allowing to output a delta animation suitable for additive blending.
- [offline] Adds fbx 20161.* sdk support.
* Build pipeline
- Adds c++11 build option for gcc/clang compilers. Use cmake ozz_build_cpp11 option.
- Automatically detects SIMD implementation based on compiler settings. SSE2 implementation is automatically enabled on x64/amd64 targets, or if /arch:SSE2 is selected on MSVC/x86 builds. One could use ozz_build_simd_ref cmake option (OZZ_BUILD_SIMD_REF preprocessor directive) to bypass detection and force reference (aka scalar) implementation. OZZ_HAS_SSE2 is now deprecated.
- Fixes #3 gcc5 warnings with simd math reference implementation.
- Fixes #6 by updating to gtest 1.70 to support new platforms (FreeBSD...).
- Adds Microsoft Visual Studio 14 2015 support.
- Adds emscripten 1.35 support.
- Integrate Coverity static analysis (https://scan.coverity.com/projects/guillaumeblanc-ozz-animation).
* Samples
- [additive] Adds an additive blending sample which demonstrates the new additive layers available through the ozz::animation::BlendingJob.
- [optimize] Adds hierarchical translation tolerance parameter to the optimize sample.
- [skin] Removes sample skin, as from now on skinning is part of the sample framework and used by other samples. See additive sample.
Release version 0.7.3
---------------------
* Changes license to the MIT License (MIT).
Release version 0.7.2
---------------------
* Library
- [animation] Improves rotations accuracy during animation sampling and blending. Quaternion normalization now uses one more Newton-Raphson step when computing inverse square root.
- [offline] Fixes fbx animation duration when take duration is different to timeline length.
- [offline] Bakes fbx axis/unit systems to all transformations, vertices, animations (and so on...), instead of using fbx sdk ConvertScene strategy which only transform scene root. This allows to mix skeleton, animation and meshes imported from any axis/unit system.
- [offline] Uses bind-pose transformation, instead of identity, for skeleton joints that are not animated in a fbx file.
- [offline] Adds support to ozz fbx tools (fbx2skel and fbx2anim) for other formats: Autodesk AutoCAD DXF (.dxf), Collada DAE (.dae), 3D Studio 3DS (.3ds) and Alias OBJ (.obj). This toolchain based on fbx sdk will replace dae toolchain (dae2skel and dae2anim) which is now deprecated.
* HowTos
- Adds file loading how-to, which demonstrates how to open a file and deserialize an object with ozz archive library.
- Adds custom skeleton importer how-to, which demonstrates RawSkeleton setup and conversion to runtime skeleton.
- Adds custom animation importer how-to, which demonstrates RawAnimation setup and conversion to runtime animation.
* Samples
- [skin] Skin sample now uses the inverse bind-pose matrices imported from the mesh file, instead of the one computed from the skeleton. This is a more robust solution, which furthermore allow to share the skeleton with meshes using different bind-poses.
- [skin] Fixes joints weight normalization when importing fbx skin meshes.
- [framework] Optimizes dynamic vertex buffer object re-allocation strategy.
Release version 0.7.1
---------------------
* Library
- [offline] Updates to fbx sdk 2015.1 with vs2013 support.
* Samples
- Adds sample_skin_fbx2skin to binary packages.
Release version 0.7.0
---------------------
* Library
- [geometry] Adds support for matrix palette skinning transformation in a new ozz_geometry library.
- [offline] Returns EXIT_FAILURE from dae2skel and fbx2skel when no skeleton found in the source file.
- [offline] Fixes fbx axis and unit system conversions.
- [offline] Removes raw_skeleton_archive.h and raw_animation_archive.h files, moving serialization definitions back to raw_skeleton.h and raw_animation.h to simplify understanding.
- [offline] Removes skeleton_archive.h and animation_archive.h files, moving serialization definitions back to skeleton.h and animation.h.
- [base] Changes Range<>::Size() definition, returning range's size in bytes instead of element count.
* Samples
- Adds a skinning sample which demonstrates new ozz_geometry SkinningJob feature and usage.
Release version 0.6.0
---------------------
* Library
- [animation] Compresses animation key frames memory footprint. Rotation key frames are compressed from 24B to 12B (50%). 3 of the 4 components of the quaternion are quantized to 2B each, while the 4th is restored during sampling. Translation and scale components are compressed to half float, reducing their size from 20B to 12B (40%).
- [animation] Changes runtime::Animation class serialization format to support compression. Serialization retro-compatibility for this class has not been implemented, meaning that all runtime::Animation must be rebuilt and serialized using usual dae2anim, fbx2anim or using offline::AnimationBuilder utility.
- [base] Adds float-to-half and half-to-float conversion functions to simd math library.
Release version 0.5.0
---------------------
* Library
- [offline] Adds --raw option to *2skel and *2anim command line tools. Allows to export raw skeleton/animation object format instead of runtime objects.
- [offline] Moves RawAnimation and RawSkeleton from the builder files to raw_animation.h and raw_skeleton.h files.
- [offline] Renames skeleton_serialize.h and animation_serialize.h to skeleton_archive.h and animation_archive.h for consistency.
- [offline] Adds RawAnimation and RawSkeleton serialization support with ozz archives.
- [options] Changes parser command line arguments type to "const char* const*" in order to support implicit casting from arguments of type "char**".
- [base] Change ozz::String std redirection from typedef to struct to be coherent with all other std containers redirection.
- [base] Moves maths archiving file from ozz/base/io to ozz/base/maths for consistency.
- [base] Adds containers serialization support with ozz archives.
- [base] Removes ozz fixed size integers in favor of standard types available with <stdint.h> file.
* Samples
- Adds Emscripten support to all supported samples.
- Changes OpenGL rendering to comply with Gles2/WebGL.
* Build pipeline
- Adds Emscripten and cross-compilation support to the builder helper python script.
- Support for CMake 3.x.
- Adds support for Microsoft Visual Studio 2013.
- Drops support for Microsoft Visual Studio 2008 and olders, as a consequence of using <stdint.h>.
Release version 0.4.0
---------------------
* Library
- [offline] Adds Fbx import pipeline, through fbx2skel and fbx2anim command line tools.
- [offline] Adds Fbx import and conversion library, through ozz_animation_fbx. Building fbx related libraries requires fbx sdk to be installed.
- [offline] Adds ozz_animation_offline_tools library to share the common work for Collada and Fbx import tools. This could be use to implement custom conversion command line tools.
* Samples
- Adds Fbx resources to media path.
- Makes use of Fbx resources with existing samples.
Release version 0.3.1
---------------------
* Samples
- Adds keyboard camera controls.
* Build pipeline
- Adds Mac OSX support, full offline and runtime pipeline, samples, dashboard...
- Moves dashboard to http://ozz.qualipilote.fr/dashboard/cdash/
- Improves dashboard configuration, using json configuration files available there: http://ozz.qualipilote.fr/dashboard/config/.
Release version 0.3.0
---------------------
* Library
- [animation] Adds partial animation blending and masking, through per-joint-weight blending coefficients.
- [animation] Switches all explicit [begin,end[ ranges (sequence of objects) to ozz::Range structure.
- [animation] Moves runtime files (.h and .cc) to a separate runtime folder (ozz/animation/runtime).
- [animation] Removes ozz/animation/utils.h and .cc
- [options] Detects duplicated command line arguments and reports failure.
- [base] Adds helper functions to ozz::memory::Allocator to support allocation/reallocation/deallocation of ranges of objects through ozz::Range structure.
* Samples
- Adds partial animation blending sample.
- Adds multi-threading sample, using OpenMp to distribute workload.
- Adds a sample that demonstrates how to attach an object to animated skeleton joints.
- Improves skeleton rendering sample utility feature: includes joint rendering.
- Adds screen-shot and video capture options from samples ui.
- Adds a command line option (--render/--norender) to enable/disable rendering of sample, used for dashboard unit-tests.
- Adds time management options, to dissociate (fix) update delta time from the real application time.
- Improves camera manipulations: disables auto-framing when zooming/panning, adds mouse wheel support for zooming.
- Fixes sample camera framing to match rendering field of view.
* Build pipeline
- Adds CMake python helper tools (build-helper.py). Removes helper .bat files (setup, build, pack...).
- Adds CDash support to generate nightly build reports. Default CDash server is http://my.cdash.org/index.php?project=Ozz.
- Adds code coverage testing support using gcov.
Release version 0.2.0
---------------------
* Library
- [animation] Adds animation blending support.
- [animation] Sets maximum skeleton joints to 1023 (aka Skeleton::kMaxJointsNumBits) to improve packing and allow stack allocations.
- [animation] Adds Skeleton::kRootIndex enum for parent index of a root joint.
- [base] Adds signed/unsigned bit shift functions to simd library.
- [base] Fixes SSE build flags for Visual Studio 64b builds.
* Samples
- Adds blending sample.
- Adds playback controller utility class to the sample framework.
Release version 0.1.0, initial open source release
--------------------------------------------------
* Library
- [animation] Support for run-time animation sampling.
- [offline] Support for building run-time animation and skeleton from a raw (aka offline/user friendly) format.
- [offline] Full Collada import pipeline (lib and tools).
- [offline] Support for animation key-frame optimizations.
- [base] Memory management redirection.
- [base] Containers definition.
- [base] Serialization and IO utilities implementation.
- [base] scalar and vector maths, SIMD (SSE) and SoA implementation.
- [options] Command line parsing utility.
* Samples
- Playback sample, loads and samples an animation.
- Millipede sample, offline pipeline usage.
- Optimize sample, offline optimization pipeline.
* Build pipeline
- CMake based build pipeline.
- CTest/GTest based unit test framework.
+112
View File
@@ -0,0 +1,112 @@
cmake_minimum_required (VERSION 3.3)
# Defines the project's name
project(ozz)
# Current version
set(OZZ_VERSION_MAJOR 0)
set(OZZ_VERSION_MINOR 13)
set(OZZ_VERSION_PATCH 0)
set(OZZ_VERSION ${OZZ_VERSION_MAJOR}.${OZZ_VERSION_MINOR}.${OZZ_VERSION_PATCH})
# Add project build options
option(ozz_build_tools "Build tools" ON)
option(ozz_build_fbx "Build Fbx pipeline (Requires Fbx SDK)" ON)
option(ozz_build_gltf "Build glTF importer (Requires c++11)" ON)
option(ozz_build_data "Build data on code change" OFF)
option(ozz_build_samples "Build samples" ON)
option(ozz_build_howtos "Build howtos" ON)
option(ozz_build_tests "Build unit tests" ON)
option(ozz_build_simd_ref "Force SIMD math reference implementation" OFF)
option(ozz_build_msvc_rt_dll "Select msvc DLL runtime library" ON)
option(ozz_build_postfix "Use per config postfix name" ON)
# Include ozz cmake parameters and scripts
include(CheckCXXCompilerFlag)
include(${PROJECT_SOURCE_DIR}/build-utils/cmake/compiler_settings.cmake)
include(${PROJECT_SOURCE_DIR}/build-utils/cmake/package_settings.cmake)
include(${PROJECT_SOURCE_DIR}/build-utils/cmake/fuse_target.cmake)
include(${PROJECT_SOURCE_DIR}/build-utils/cmake/clang_format.cmake)
# Add project execution options
option(ozz_run_tests_headless "Run samples without rendering (used for unit tests)" ON)
set(ozz_sample_testing_loops "20" CACHE STRING "Number of loops while running sample tests (used for unit tests)")
# Configure CMake module path
set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} "${PROJECT_SOURCE_DIR}/build-utils/cmake/modules/")
# Detects Fbx SDK, required to build Fbx pipeline.
if(ozz_build_tools AND ozz_build_fbx)
# Select a msvc runtime compatible with ozz_build_msvc_rt_dll
set(FBX_MSVC_RT_DLL ${ozz_build_msvc_rt_dll})
# Search for FBX sdk package
find_package(Fbx 2016)
# Disables ozz_build_fbx if Fbx SDK isn't found.
if(NOT FBX_FOUND)
message("Fbx SDK not found, FBX tools libraries and samples will be skipped.")
set(ozz_build_fbx OFF)
endif()
else()
# Disables fbx if tools are disabled
set(ozz_build_fbx OFF)
endif()
# gltf
if(ozz_build_tools AND ozz_build_gltf)
else()
set(ozz_build_gltf OFF)
endif()
# Enables unit tests.
if(ozz_build_tests)
enable_testing()
endif()
# Locates media directory.
set(ozz_media_directory "${PROJECT_SOURCE_DIR}/media")
# Creates temporary directory for tests inputs/outputs.
set(ozz_temp_directory ${PROJECT_BINARY_DIR}/temp)
file(MAKE_DIRECTORY ${ozz_temp_directory})
# Outputs selected options (can be modified by the command line)
message("-- ---------------------------------------------------------")
message("-- Selected options:")
message("-- - ozz_build_tools: " ${ozz_build_tools})
message("-- - ozz_build_fbx: " ${ozz_build_fbx})
message("-- - ozz_build_gltf: " ${ozz_build_gltf})
message("-- - ozz_build_data: " ${ozz_build_data})
message("-- - ozz_build_samples: " ${ozz_build_samples})
message("-- - ozz_build_howtos: " ${ozz_build_howtos})
message("-- - ozz_build_tests: " ${ozz_build_tests})
message("-- - ozz_build_simd_ref: " ${ozz_build_simd_ref})
message("-- - ozz_build_msvc_rt_dll: " ${ozz_build_msvc_rt_dll})
message("-- - ozz_build_postfix: " ${ozz_build_postfix})
# Starts building the sources tree
add_subdirectory(src)
# Continues with howtos
if(ozz_build_howtos AND NOT EMSCRIPTEN)
add_subdirectory(howtos)
endif()
# Continues with samples
if(ozz_build_samples)
add_subdirectory(samples)
endif()
# Continues with the tests tree
if(ozz_build_tests AND NOT EMSCRIPTEN)
add_subdirectory(test)
endif()
install(FILES
${PROJECT_SOURCE_DIR}/CHANGES.md
${PROJECT_SOURCE_DIR}/LICENSE.md
${PROJECT_SOURCE_DIR}/README.md
DESTINATION ./)
+16
View File
@@ -0,0 +1,16 @@
Thanks a lot for considering a contribution to ozz-animation! All contributions are welcome: code reviews, bug reports, bug fixes, samples, features, platforms, testing, documentation, optimizations...
# Submitting bugs
To report bugs please use [project's issues tracker](https://github.com/guillaumeblanc/ozz-animation/issues). To help with debugging and understanding, please provide a simple repro case, ideally a modified [sample](https://github.com/guillaumeblanc/ozz-animation/tree/master/samples) or [howto](https://github.com/guillaumeblanc/ozz-animation/tree/master/howtos) with minimal changes.
# Contributing to the code
**By submitting a pull request for this project, you agree to license your contribution under [project's MIT license](LICENSE.md).**
ozz branching strategy follows [gitflow model](http://nvie.com/posts/a-successful-git-branching-model/). When submitting patches, please:
- Make pull requests to develop branch for features, to release branch for hotfixes.
- Respect [Google c++ coding style](https://google.github.io/styleguide/cppguide.html), run clang-format.
- Implement all relevant unit tests.
- Run all the tests and make sure they pass.
- Add your name and email address at the end of [AUTHORS.md](AUTHORS.md) list.
+23
View File
@@ -0,0 +1,23 @@
ozz-animation is hosted at http://github.com/guillaumeblanc/ozz-animation and
distributed under the MIT License (MIT).
---
Copyright (c) 2020 Guillaume Blanc
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is 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 Software.
THE SOFTWARE IS 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 SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+45
View File
@@ -0,0 +1,45 @@
[![logo](media/icon/ozz-grey-256.png)](http://guillaumeblanc.github.io/ozz-animation/)
ozz-animation
=============
open source c++ 3d skeletal animation library and toolset
---------------------------------------------------------
ozz-animation provides runtime character animation playback functionalities (loading, sampling, blending...). It proposes a low-level renderer agnostic and game-engine agnostic implementation, focusing on performance and memory constraints with a data-oriented design.
ozz-animation comes with the toolchain to convert from major Digital Content Creation formats (gltf, Fbx, Collada, Obj, 3ds, dxf) to ozz optimized runtime structures. Offline libraries are also provided to implement the conversion from any other animation and skeleton format.
Documentation
-------------
Documentation and samples are available from [ozz-animation website](http://guillaumeblanc.github.io/ozz-animation/). Join [Gitter](https://gitter.im/ozz-animation/community) for further discussions.
Supported platforms
-------------------
Ozz is tested on Linux, Mac OS and Windows, for x86, x86-64 and ARM architectures. The run-time code (ozz_base, ozz_animation, ozz_geometry) depends only on c++11, the standard CRT and has no OS specific code, portability to any other platform shouldn't be an issue.
Samples, tools and tests depend on external libraries (glfw, tinygltf, Fbx SDK, jsoncpp, gtest, ...), which could limit portability.
Build status
------------
| | Linux | Mac OS | Windows |
| ------- | ------ | ------ | ------- |
| master | [![Travis-CI](https://travis-ci.org/guillaumeblanc/ozz-animation.svg?branch=master)](http://travis-ci.org/guillaumeblanc/ozz-animation) | [![Travis-CI](https://travis-ci.org/guillaumeblanc/ozz-animation.svg?branch=master)](http://travis-ci.org/guillaumeblanc/ozz-animation) | [![AppVeyor](https://ci.appveyor.com/api/projects/status/github/guillaumeblanc/ozz-animation?branch=master&svg=true)](http://ci.appveyor.com/project/guillaumeblanc/ozz-animation) |
| develop | [![Travis-CI](https://travis-ci.org/guillaumeblanc/ozz-animation.svg?branch=develop)](http://travis-ci.org/guillaumeblanc/ozz-animation) | [![Travis-CI](https://travis-ci.org/guillaumeblanc/ozz-animation.svg?branch=develop)](http://travis-ci.org/guillaumeblanc/ozz-animation) | [![AppVeyor](https://ci.appveyor.com/api/projects/status/github/guillaumeblanc/ozz-animation?branch=develop&svg=true)](http://ci.appveyor.com/project/guillaumeblanc/ozz-animation) |
The dashboard for all branches is available [here](http://guillaumeblanc.github.io/ozz-animation/documentation/dashboard/).
Contributing
------------
All contributions are welcome: code reviews, bug reports, bug fixes, samples, features, platforms, testing, documentation, optimizations...
Please read [CONTRIBUTING](CONTRIBUTING.md) file for more details about how to submit bugs or contribute to the code.
License
-------
ozz-animation is hosted on [github](http://github.com/guillaumeblanc/ozz-animation/) and distributed under the **MIT License** (MIT).
+88
View File
@@ -0,0 +1,88 @@
version: '{build}'
image: Visual Studio 2019
environment:
matrix:
# Comilers matrix
- env_cmake_generator: "Visual Studio 14 2015"
APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2015
env_cmake_configuration: Debug
env_fbxsdk_path: "http://www.autodesk.com/content/dam/autodesk/www/adn/fbx/20195/fbx20195_fbxsdk_vs2015_win.exe"
- env_cmake_generator: "Visual Studio 14 2015 Win64"
APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2015
env_cmake_configuration: Debug
env_fbxsdk_path: "http://www.autodesk.com/content/dam/autodesk/www/adn/fbx/20195/fbx20195_fbxsdk_vs2015_win.exe"
- env_cmake_generator: "Visual Studio 15 2017"
APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2017
env_cmake_configuration: Debug
env_fbxsdk_path: "http://www.autodesk.com/content/dam/autodesk/www/adn/fbx/20195/fbx20195_fbxsdk_vs2017_win.exe"
- env_cmake_generator: "Visual Studio 15 2017 Win64"
APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2017
env_cmake_configuration: Debug
env_fbxsdk_path: "http://www.autodesk.com/content/dam/autodesk/www/adn/fbx/20195/fbx20195_fbxsdk_vs2017_win.exe"
- env_cmake_generator: "Visual Studio 15 2017"
APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2017
env_cmake_configuration: Release
env_fbxsdk_path: "http://www.autodesk.com/content/dam/autodesk/www/adn/fbx/20195/fbx20195_fbxsdk_vs2017_win.exe"
- env_cmake_generator: "Visual Studio 15 2017 Win64"
APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2017
env_cmake_configuration: Release
env_fbxsdk_path: "http://www.autodesk.com/content/dam/autodesk/www/adn/fbx/20195/fbx20195_fbxsdk_vs2017_win.exe"
- env_cmake_generator: "Visual Studio 16 2019"
env_cmake_configuration: Debug
env_fbxsdk_path: "http://www.autodesk.com/content/dam/autodesk/www/adn/fbx/20195/fbx20195_fbxsdk_vs2017_win.exe"
- env_cmake_generator: "Visual Studio 16 2019"
env_cmake_configuration: Release
env_fbxsdk_path: "http://www.autodesk.com/content/dam/autodesk/www/adn/fbx/20195/fbx20195_fbxsdk_vs2017_win.exe"
- env_cmake_generator: "Visual Studio 16 2019"
env_cmake_configuration: Release
env_fbxsdk_path: "http://www.autodesk.com/content/dam/autodesk/www/adn/fbx/20195/fbx20195_fbxsdk_vs2017_win.exe"
env_build_msvc_rt_dll: "1"
- env_cmake_generator: "Visual Studio 16 2019"
env_cmake_configuration: Release
env_fbxsdk_path: "http://www.autodesk.com/content/dam/autodesk/www/adn/fbx/20195/fbx20195_fbxsdk_vs2017_win.exe"
env_build_msvc_rt_dll: "0"
# No fbx sdk
- env_cmake_generator: "Visual Studio 16 2019"
env_cmake_configuration: Release
# Use ozz as a sub project (should set msvc rt dll for ozz as this is the default in cmake)
- env_cmake_generator: "Visual Studio 16 2019"
env_cmake_configuration: Release
env_src_root: "../test/sub/"
env_fbxsdk_path: "http://www.autodesk.com/content/dam/autodesk/www/adn/fbx/20195/fbx20195_fbxsdk_vs2017_win.exe"
- env_cmake_generator: "Visual Studio 16 2019"
env_cmake_configuration: Debug
env_src_root: "../test/sub/"
env_fbxsdk_path: "http://www.autodesk.com/content/dam/autodesk/www/adn/fbx/20195/fbx20195_fbxsdk_vs2017_win.exe"
install:
# Setup Fbx sdk
- ps: >-
if ($Env:env_fbxsdk_path) {
md fbx
cd fbx
Start-FileDownload $Env:env_fbxsdk_path "fbxsdk.exe"
Start-Process -FilePath "fbxsdk.exe" /S -Wait
cd ..
}
# Fixes up env_src_root if it isn't defined
- ps: >-
if (!$Env:env_src_root) {
$Env:env_src_root=".."
}
# Fixes up env_build_msvc_rt_dll if it isn't defined
- ps: >-
if (!$Env:env_build_msvc_rt_dll) {
$Env:env_build_msvc_rt_dll="1"
}
build_script:
- cmake --version
- mkdir build
- cd build
- cmake -G "%env_cmake_generator%" -Dozz_build_tests=1 -Dozz_build_data=1 -Dozz_build_msvc_rt_dll=%env_build_msvc_rt_dll% -DCMAKE_BUILD_TYPE=%env_cmake_configuration% %env_src_root%
- cmake --build ./ --config %env_cmake_configuration%
test_script:
- ctest --build-config %env_cmake_configuration%
+388
View File
@@ -0,0 +1,388 @@
#!/usr/bin/python
#----------------------------------------------------------------------------#
# #
# ozz-animation is hosted at http://github.com/guillaumeblanc/ozz-animation #
# and distributed under the MIT License (MIT). #
# #
# Copyright (c) 2019 Guillaume Blanc #
# #
# Permission is hereby granted, free of charge, to any person obtaining a #
# copy of this software and associated documentation files (the "Software"), #
# to deal in the Software without restriction, including without limitation #
# the rights to use, copy, modify, merge, publish, distribute, sublicense, #
# and/or sell copies of the Software, and to permit persons to whom the #
# Software is 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 Software. #
# #
# THE SOFTWARE IS 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 SOFTWARE OR THE USE OR OTHER #
# DEALINGS IN THE SOFTWARE. #
# #
#----------------------------------------------------------------------------#
# CMake python helper script.
import subprocess
import shutil
import sys
import os
import os.path
import re
import platform
from functools import partial
# Build global path variables.
root = os.path.abspath(os.path.join(os.getcwd(), '.'))
build_dir = os.path.join(root, 'build')
build_dir_cc = os.path.join(root, 'build-cc')
cmake_cache_file = os.path.join(build_dir, 'CMakeCache.txt')
ctest_cache_file = os.path.join(build_dir, 'CTestTestfile.cmake')
config = 'Release'
generators = {0: 'default'}
generator = generators[0]
enable_testing = False
emscripten_path = os.environ.get('EMSCRIPTEN')
def ValidateCMake():
try:
# Test that cmake can be executed, silently...
pipe = subprocess.Popen(['cmake'], stdout=subprocess.PIPE, stderr=subprocess.PIPE)
out, err = pipe.communicate()
except OSError as e:
print("CMake is not installed or properly setup. Please visit www.cmake.org.")
return False
print("CMake is installed and setup properly.")
return True
def CheckEmscripten():
if(emscripten_path == None):
return False
try:
# Test that cmake can be executed, silently...
pipe = subprocess.Popen(['emcc'], stdout=subprocess.PIPE, stderr=subprocess.PIPE)
out, err = pipe.communicate()
except OSError as e:
print("Emscripten is not installed or properly setup.")
return False
print("Emscripten is installed and setup properly.")
return True
def MakeBuildDir(_build_dir = build_dir):
print("Creating out-of-source build directory: \"" + _build_dir + "\".")
if not os.path.exists(_build_dir):
os.makedirs(_build_dir)
return True
def CleanBuildDir():
print("Deleting out-of-source build directory: \"" + build_dir + "\".")
if os.path.exists(build_dir):
shutil.rmtree(build_dir)
print("Deleting out-of-source cross compilation build directory: \"" + build_dir_cc + "\".")
if os.path.exists(build_dir_cc):
shutil.rmtree(build_dir_cc)
return True
def Configure():
# Configure build process.
print("Configuring build project.")
options = ['cmake']
options += ['-D', 'CMAKE_BUILD_TYPE=' + config]
if (enable_testing) :
options += ['-D', 'ozz_build_tests=1']
else:
options += ['-D', 'ozz_build_tests=0']
global generator
if(generator != 'default'):
options += ['-G', generator]
options += [root]
config_process = subprocess.Popen(options, cwd=build_dir)
config_process.wait()
if(config_process.returncode != 0):
print("Configuration failed.")
return False
print("Configuration succeeded.")
# Updates generator once configuration is complete
generator = DetectGenerator()
return True
def ConfigureCC():
# Configure build process.
print("Configuring emscripten cross compilation build with path: " + emscripten_path)
options = ['cmake']
options += ['-D', 'CMAKE_BUILD_TYPE=' + config]
options += ['-D', 'CMAKE_TOOLCHAIN_FILE=' + emscripten_path + '/cmake/Modules/Platform/Emscripten.cmake']
if(platform.system() == 'Windows'):
options += ['-G', 'MinGW Makefiles']
else:
options += ['-G', 'Unix Makefiles']
options += [root]
config_process = subprocess.Popen(options, cwd=build_dir_cc)
config_process.wait()
if(config_process.returncode != 0):
print("Configuration failed.")
return False
print("Configuration succeeded.")
# Updates generator once configuration is complete
generator = DetectGenerator()
return True
def Build(_build_dir = build_dir):
# Configure build process.
print("Building project.")
options = ['cmake', '--build', _build_dir, '--config', config, '--use-stderr'];
# Appends parallel build option if supported by the generator.
if "Unix Makefiles" in generator:
options += ['--', '-j4']
config_process = subprocess.Popen(options, cwd=_build_dir)
config_process.wait()
if(config_process.returncode != 0):
print("Build failed.")
return False
print("Build succeeded.")
return True
def Test():
# Configure Test process, parallelize a lot of tests in order to stress their dependencies
print("Running unit tests.")
options = ['ctest' ,'--output-on-failure', '-j8', '--build-config', config]
config_process = subprocess.Popen(options, cwd=build_dir)
config_process.wait()
if(config_process.returncode != 0):
print("Testing failed.")
return False
print("Testing succeeded.")
return True
def PackSources(_type):
print("Packing sources.")
options = ['cpack', '-G', _type, '--config', 'CPackSourceConfig.cmake']
config_process = subprocess.Popen(options, cwd=build_dir)
config_process.wait()
if(config_process.returncode != 0):
print("Packing sources of type " + _type + " failed.")
return False
print("Packing sources of type " + _type + " succeeded.")
return True
def PackBinaries(_type, _build_dir = build_dir):
print("Packing binaries.")
options = ['cpack', '-G', _type, '-C', config]
config_process = subprocess.Popen(options, cwd=_build_dir)
config_process.wait()
if(config_process.returncode != 0):
print("Packing binaries of type " + _type + " failed.")
return False
print("Packing binaries of type " + _type + " succeeded.")
return True
def SelecConfig():
configs = {
1: 'Debug',
2: 'Release',
3: 'RelWithDebInfo',
4: 'MinSizeRel'}
while True:
print("Select build configuration:")
for num, message in sorted(configs.iteritems()):
print("%d: %s") % (num, message)
# Get input and check validity
try:
answer = int(raw_input("Enter a value: "))
except:
continue
if not answer in configs:
continue
# Affect global configuration variable
global config
config = configs[answer]
return True
def FindGenerators():
# Finds all generators outputted from cmake usage
process = subprocess.Popen(['cmake', '--help'], stdout=subprocess.PIPE)
stdout = process.communicate()[0]
sub_stdout = stdout[stdout.rfind('Generators'):]
matches = re.findall(r"\s*\**\s*(.+)\s*=.+", sub_stdout, re.MULTILINE)
# Fills generators list
global generators
for match in matches:
generator_name = match.strip()
# Appends also Win64/ARM option if generator is VS
if " [arch]" in generator_name:
gen_name = generator_name[0:len(generator_name) - 7]
generators[len(generators)] = gen_name
generators[len(generators)] = gen_name + " Win64"
generators[len(generators)] = gen_name + " ARM"
else:
generators[len(generators)] = generator_name
def FindInCache(_regex):
try:
cache_file = open(cmake_cache_file)
except:
return None
return re.search(_regex, cache_file.read())
def DetectGenerator():
match = FindInCache(r"CMAKE_GENERATOR:INTERNAL=(.*)")
if match:
global generators
global generator
for num, message in sorted(generators.iteritems()):
if match.group(1) == message:
return message
return 'default'
def SelecGenerator():
global generators
while True:
print("Select generator:")
for num, message in sorted(generators.iteritems()):
print("%d: %s") % (num, message)
# Get input and check validity
try:
answer = int(raw_input("Enter a value: "))
except:
continue
if not answer in generators:
continue
# Check if this is the current generator
current_generator = DetectGenerator()
if current_generator == 'default':
global generator
generator = generators[answer]
return True
if current_generator != generators[answer]:
print("Selected generator '%s' is different from the current one '%s'.") % (generators[answer], current_generator)
clean = raw_input("Do you want to clean build directory to apply the change? (y/n): ") == "y"
if clean:
generator = generators[answer]
return CleanBuildDir()
return True
def DetectTesting():
global enable_testing
enable_testing = os.path.isfile(ctest_cache_file)
def EnableTesting():
global enable_testing
while True:
# Get input and check validity
answer = raw_input("enable testing (y/n): ")
if answer != 'y' and answer != 'n':
continue
wanted = (answer == 'y')
# Get current state
if (enable_testing != wanted):
enable_testing = wanted
print("Testing state has changed.")
return True
def ClearScreen():
os.system('cls' if os.name=='nt' else 'clear')
def Quit():
sys.exit(0)
return True
def main():
# Checks CMake installation is correct.
if not ValidateCMake():
return
# Emscripten is optional
CheckEmscripten()
# Detects available generators
FindGenerators()
# Detects testing state
DetectTesting()
# Update current generator
print("DetectGenerator")
global generator
generator = DetectGenerator()
options = {
'1': ["Build", [MakeBuildDir, Configure, Build]],
'2': ["Run unit tests", [MakeBuildDir, Configure, Build, Test]],
'3': ["Execute CMake generation step (don't build)", [MakeBuildDir, Configure]],
'4': ["Clean out-of-source build directory\n ------------------", [CleanBuildDir]],
'5': ["Pack binaries", [MakeBuildDir, Configure, Build, partial(PackBinaries, "ZIP"), partial(PackBinaries, "TBZ2")]],
'6': ["Pack sources\n ------------------", [MakeBuildDir, Configure, partial(PackSources, "ZIP"), partial(PackSources, "TBZ2")]],
'7': ["Enable testing", [EnableTesting]],
'8': ["Select build configuration", [SelecConfig]],
'9': ["Select cmake generator\n ------------------", [SelecGenerator]],
'q': ["Quit\n------------------", [Quit]]}
# Adds emscripten
global emscripten_path
if emscripten_path != None:
options['1a'] = ["Build emscripten", [partial(MakeBuildDir, build_dir_cc), ConfigureCC, partial(Build, build_dir_cc)]]
options['5a'] = ["Pack emscripten binaries", [MakeBuildDir, Configure, Build, partial(MakeBuildDir, build_dir_cc), ConfigureCC, partial(Build, build_dir_cc), partial(PackBinaries, "ZIP", build_dir_cc)]]
while True:
# Displays options
ClearScreen()
print("ozz CMake build helper tool")
print("")
print("Selected build configuration: %s") % config
print("Selected generator: %s") % generator
print("Testing enabled: %s") % enable_testing
print("")
print("Choose an option:")
print("------------------")
for key, message in sorted(options.iteritems()):
print(" %s: %s") % (key, message[0])
# Get input and check validity
answer = raw_input("Enter a value: ")
if not answer in options:
continue
# Execute command in a try catch to avoid crashes and allow retries.
ClearScreen()
try:
for command in options[answer][1]:
if command():
print("\nExecution success.\n")
else:
print("\nExecution failed.\n")
break
except Exception as e:
print("\nAn error occured during script execution: %s\n") % e
raw_input("Press enter to continue...")
return 0
if __name__ == '__main__':
main()
@@ -0,0 +1,22 @@
# Apply clang-format utility (if found) to all sources.
#------------------------------------------------------
find_program(CLANG_FORMAT "clang-format")
if(CLANG_FORMAT)
message("clang-format found, adding target to the build process.")
file(GLOB_RECURSE
all_source_files
"include/*.h"
"src/*.cc" "src/*.h"
"test/*.cc" "test/*.h"
"samples/*.cc" "samples/*.h"
"howtos/*.cc")
add_custom_target(
BUILD_CLANG_FORMAT
COMMAND ${CLANG_FORMAT} -i -style=google ${all_source_files}
VERBATIM)
else()
message("Optional program clang-format not found.")
endif()
@@ -0,0 +1,160 @@
# Set compilers settings for all platforms/compilers.
#---------------------------------------------------
#-----------------
# Includes modules
include(CheckIncludeFiles)
#------------------------------
# Enables IDE folders y default
set_property(GLOBAL PROPERTY USE_FOLDERS ON)
#------------------------
# Available build options
#------------------------
# Lists all the cxx flags
set(cxx_all_flags
CMAKE_CXX_FLAGS
CMAKE_C_FLAGS
CMAKE_CXX_FLAGS_DEBUG
CMAKE_C_FLAGS_DEBUG
CMAKE_CXX_FLAGS_MINSIZEREL
CMAKE_C_FLAGS_MINSIZEREL
CMAKE_CXX_FLAGS_RELWITHDEBINFO
CMAKE_C_FLAGS_RELWITHDEBINFO
CMAKE_CXX_FLAGS_RELEASE
CMAKE_C_FLAGS_RELEASE)
#--------------------------------------
# Cross compiler compilation flags
# Requires C++11
set(CMAKE_CXX_STANDARD 11)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
set(CMAKE_CXX_EXTENSIONS OFF)
# Simd math force ref
if(ozz_build_simd_ref)
set_property(DIRECTORY APPEND PROPERTY COMPILE_DEFINITIONS OZZ_BUILD_SIMD_REF)
endif()
#--------------------------------------
# Modify default MSVC compilation flags
if(MSVC)
#---------------------------
# For the common build flags
# Disables crt secure warnings
set_property(DIRECTORY APPEND PROPERTY COMPILE_DEFINITIONS _CRT_SECURE_NO_WARNINGS)
# Adds support for multiple processes builds
set_property(DIRECTORY APPEND PROPERTY COMPILE_OPTIONS "/MP")
# Set the warning level to W4
set_property(DIRECTORY APPEND PROPERTY COMPILE_OPTIONS "/W4")
# Set warning as error
set_property(DIRECTORY APPEND PROPERTY COMPILE_OPTIONS "/WX")
# Select whether to use the DLL version or the static library version of the Visual C++ runtime library.
foreach(flag ${cxx_all_flags})
if (ozz_build_msvc_rt_dll)
string(REGEX REPLACE "/MT" "/MD" ${flag} "${${flag}}")
else()
string(REGEX REPLACE "/MD" "/MT" ${flag} "${${flag}}")
endif()
endforeach()
#--------------------------------------
# else consider the compiler as GCC compatible
# Modify default GCC compilation flags
else()
# Set the warning level to Wall
set_property(DIRECTORY APPEND PROPERTY COMPILE_OPTIONS "-Wall")
# Enable extra level of warning
#set_property(DIRECTORY APPEND PROPERTY COMPILE_OPTIONS "-Wextra")
# Set warning as error
set_property(DIRECTORY APPEND PROPERTY COMPILE_OPTIONS "-Werror")
# Disables warning: ignored-attributes reports issue when using _m128 as template argument
check_cxx_compiler_flag("-Wignored-attributes" W_IGNORED_ATTRIBUTES)
if(W_IGNORED_ATTRIBUTES)
set_property(DIRECTORY APPEND PROPERTY COMPILE_OPTIONS "-Wno-ignored-attributes")
endif()
# Enables warning: sign comparison warnings
check_cxx_compiler_flag("-Wsign-compare" W_SIGN_COMPARE)
if(W_SIGN_COMPARE)
set_property(DIRECTORY APPEND PROPERTY COMPILE_OPTIONS "-Wsign-compare")
endif()
# Check some more options availability for the targeted compiler
check_cxx_compiler_flag("-Wnull-dereference" W_NULL_DEREFERENCE)
check_cxx_compiler_flag("-Wpragma-pack" W_PRAGMA_PACK)
# Enables debug glibcxx if NDebug isn't defined, not supported by APPLE
if(NOT APPLE)
set_property(DIRECTORY APPEND PROPERTY COMPILE_DEFINITIONS "$<$<CONFIG:Debug>:_GLIBCXX_DEBUG>")
endif()
#----------------------
# Sets emscripten output
if(EMSCRIPTEN)
SET(CMAKE_EXECUTABLE_SUFFIX ".html")
add_link_options(-s DISABLE_DEPRECATED_FIND_EVENT_TARGET_BEHAVIOR=0)
#if(NOT ozz_build_simd_ref)
# set_property(DIRECTORY APPEND PROPERTY COMPILE_OPTIONS "-msse2")
#endif()
endif()
endif()
#---------------------
# Prints all the flags
message(STATUS "---------------------------------------------------------")
message(STATUS "Default build type is: ${CMAKE_BUILD_TYPE}")
message(STATUS "The following compilation flags will be used:")
foreach(flag ${cxx_all_flags})
message(${flag} " ${${flag}}")
endforeach()
message(STATUS "---------------------------------------------------------")
get_directory_property(DirectoryCompileOptions DIRECTORY ${PROJECT_SOURCE_DIR} COMPILE_OPTIONS)
message(STATUS "Directory Compile Options:")
foreach(opt ${DirectoryCompileOptions})
message(STATUS ${opt})
endforeach()
message(STATUS "---------------------------------------------------------")
get_directory_property(DirectoryCompileDefinitions DIRECTORY ${PROJECT_SOURCE_DIR} COMPILE_DEFINITIONS)
message(STATUS "Directory Compile Definitions:")
foreach(def ${DirectoryCompileDefinitions})
message(STATUS ${def})
endforeach()
message(STATUS "---------------------------------------------------------")
#----------------------------------------------
# Modifies output directory for all executables
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ".")
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY_DEBUG ".")
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY_RELEASE ".")
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY_MINSIZEREL ".")
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY_RELWITHDEBINFO ".")
#-------------------------------
# Set a postfix for output files
if(ozz_build_postfix)
set(CMAKE_DEBUG_POSTFIX "_d")
set(CMAKE_RELEASE_POSTFIX "_r")
set(CMAKE_MINSIZEREL_POSTFIX "_rs")
set(CMAKE_RELWITHDEBINFO_POSTFIX "_rd")
endif()
@@ -0,0 +1,27 @@
# Fuses all target .cc sources in a single file.
#-----------------------------------------------
function(fuse_target _target_name)
set(output_file_name "${_target_name}.cc")
set(output_file "${PROJECT_BINARY_DIR}/src_fused/${output_file_name}")
# Get all target sources.
get_property(target_source_files TARGET ${_target_name} PROPERTY SOURCES)
add_custom_command(
OUTPUT ${output_file}
DEPENDS ${target_source_files}
${PROJECT_SOURCE_DIR}/build-utils/cmake/fuse_target_script.cmake
COMMAND ${CMAKE_COMMAND} -Dozz_fuse_output_file="${output_file}" -Dozz_target_source_files="${target_source_files}" -Dozz_fuse_target_dir="${CMAKE_CURRENT_LIST_DIR}" -Dozz_fuse_src_dir="${PROJECT_SOURCE_DIR}" -P "${PROJECT_SOURCE_DIR}/build-utils/cmake/fuse_target_script.cmake")
add_custom_target(BUILD_FUSE_${_target_name} ALL DEPENDS ${output_file})
set_target_properties(BUILD_FUSE_${_target_name} PROPERTIES FOLDER "ozz/fuse")
if (NOT TARGET BUILD_FUSE_ALL)
add_custom_target(BUILD_FUSE_ALL ALL)
endif()
add_dependencies(BUILD_FUSE_ALL BUILD_FUSE_${_target_name})
endfunction()
@@ -0,0 +1,37 @@
# For each library, fuses all sources to a single .cc file.
#----------------------------------------------------------
# Start with new content
string(CONCAT output_content "" "// This file is autogenerated. Do not modify it.\n\n")
# Patches arguments so that cmake interprate it as a list.
string (REPLACE " " ";" ozz_target_source_files "${ozz_target_source_files}")
# Concat all sources to the output.
foreach(src_file ${ozz_target_source_files})
get_filename_component(src_file_ext ${src_file} EXT)
# Handle source files.
if(src_file_ext STREQUAL ".cc")
file(READ "${ozz_fuse_target_dir}/${src_file}" src_file_content)
string(CONCAT output_content "${output_content}" "// Including ${src_file} file.\n\n")
string(CONCAT output_content "${output_content}" "${src_file_content}\n")
endif()
endforeach()
# Handle private include files (they are not prefixed by "ozz/").
string(REGEX MATCHALL "#include \"[\^\"ozz\"]([^\"]+)\"" internal_include_lines ${output_content})
foreach(internal_include_line ${internal_include_lines})
STRING(REGEX REPLACE "#include \"([^\"]+)\"" "\\1" internal_include_file "${internal_include_line}" )
file(READ "${ozz_fuse_src_dir}/src/${internal_include_file}" internal_src_file_content)
string(REPLACE "${internal_include_line}" "\n// Includes internal include file ${internal_include_file}\n\n${internal_src_file_content}" output_content "${output_content}")
endforeach()
file(WRITE "${ozz_fuse_output_file}" "${output_content}")
@@ -0,0 +1,274 @@
# This module will try to located FBX SDK folder, based on the standard
# directory structure proposed by Autodesk.
# On every platform, the module will look for libraries that matches the
# currently selected cmake generator.
# A version can be specified to the find_package function.
#
# Once done, it will define
# FBX_FOUND - System has Fbx SDK installed
# FBX_INCLUDE_DIRS - The Fbx SDK include directories
# FBX_LIBRARIES - The libraries needed to use Fbx SDK
# FBX_LIBRARIES_DEBUG - The libraries needed to use debug Fbx SDK
#
# It accepts the following variables as input:
#
# FBX_MSVC_RT_DLL - Optional. Select whether to use the DLL version or the
# static library version of the Visual C++ runtime library.
# Default is ON (aka, DLL version: /MD).
#
# Known issues:
# - On ALL platforms: If there are multiple FBX SDK version installed, the
# current implementation will select the first one it finds.
# - On MACOS: If there are multiple FBX SDK compiler supported (clang or gcc),
# the current implementation will select the first one it finds.
#----------------------------------------------------------------------------#
# #
# ozz-animation is hosted at http://github.com/guillaumeblanc/ozz-animation #
# and distributed under the MIT License (MIT). #
# #
# Copyright (c) 2019 Guillaume Blanc #
# #
# Permission is hereby granted, free of charge, to any person obtaining a #
# copy of this software and associated documentation files (the "Software"), #
# to deal in the Software without restriction, including without limitation #
# the rights to use, copy, modify, merge, publish, distribute, sublicense, #
# and/or sell copies of the Software, and to permit persons to whom the #
# Software is 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 Software. #
# #
# THE SOFTWARE IS 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 SOFTWARE OR THE USE OR OTHER #
# DEALINGS IN THE SOFTWARE. #
# #
#----------------------------------------------------------------------------#
###############################################################################
# Generic library search function definition
###############################################################################
function(FindFbxLibrariesGeneric _FBX_ROOT_DIR _OUT_FBX_LIBRARIES _OUT_FBX_LIBRARIES_DEBUG)
# Directory structure depends on the platform:
# - Windows: \lib\<compiler_version>\<processor_type>\<build_mode>
# - Mac OSX: \lib\<compiler_version>\ub\<processor_type>\<build_mode>
# - Linux: \lib\<compiler_version>\<build_mode>
# Figures out matching compiler/os directory.
if("x${CMAKE_CXX_COMPILER_ID}" STREQUAL "xMSVC")
if(NOT CMAKE_CXX_COMPILER_VERSION VERSION_LESS 19.10)
set(FBX_CP_PATH "vs2017")
elseif(NOT CMAKE_CXX_COMPILER_VERSION VERSION_LESS 19)
set(FBX_CP_PATH "vs2015")
elseif(NOT CMAKE_CXX_COMPILER_VERSION VERSION_LESS 18)
set(FBX_CP_PATH "vs2013")
elseif(NOT CMAKE_CXX_COMPILER_VERSION VERSION_LESS 17)
set(FBX_CP_PATH "vs2012")
elseif(NOT CMAKE_CXX_COMPILER_VERSION VERSION_LESS 16)
set(FBX_CP_PATH "vs2010")
else()
message ("Unsupported MSVC compiler version ${CMAKE_CXX_COMPILER_VERSION}.")
return()
endif()
elseif(APPLE)
set(FBX_CP_PATH "*")
else()
set(FBX_CP_PATH "*")
endif()
# Detects current processor type.
if(NOT APPLE) # No <processor_type> on APPLE platform
if(CMAKE_SIZEOF_VOID_P EQUAL 8)
set(FBX_PROCESSOR_PATH "x64")
else()
set(FBX_PROCESSOR_PATH "x86")
endif()
endif()
# Set libraries names to search, sorted by preference.
set(FBX_SEARCH_LIB_NAMES fbxsdk-static.a libfbxsdk.a fbxsdk.a)
# Select whether to use the DLL version or the static library version of the Visual C++ runtime library.
# Default is "md", aka use the multithread DLL version of the run-time library.
if (NOT DEFINED FBX_MSVC_RT_DLL OR FBX_MSVC_RT_DLL)
set(FBX_SEARCH_LIB_NAMES ${FBX_SEARCH_LIB_NAMES} libfbxsdk-md.lib)
else()
set(FBX_SEARCH_LIB_NAMES ${FBX_SEARCH_LIB_NAMES} libfbxsdk-mt.lib)
endif()
# Set search path.
set(FBX_SEARCH_LIB_PATH "${_FBX_ROOT_DIR}/lib/${FBX_CP_PATH}/${FBX_PROCESSOR_PATH}")
find_library(FBX_LIB
${FBX_SEARCH_LIB_NAMES}
HINTS "${FBX_SEARCH_LIB_PATH}/release/")
if(FBX_LIB)
# Searches debug version also
find_library(FBX_LIB_DEBUG
${FBX_SEARCH_LIB_NAMES}
HINTS "${FBX_SEARCH_LIB_PATH}/debug/")
if(UNIX)
if(APPLE) # APPLE requires to link with Carbon framework
find_library(CARBON_FRAMEWORK Carbon)
list(APPEND FBX_LIB ${CARBON_FRAMEWORK})
list(APPEND FBX_LIB_DEBUG ${CARBON_FRAMEWORK})
else()
find_package(Threads)
list(APPEND FBX_LIB ${CMAKE_THREAD_LIBS_INIT} dl)
list(APPEND FBX_LIB_DEBUG ${CMAKE_THREAD_LIBS_INIT} dl)
endif()
endif()
FindFbxVersion(${FBX_ROOT_DIR} PATH_VERSION)
# 2019 SDK needs to link against bundled libxml and zlib
if(PATH_VERSION GREATER_EQUAL "2019.1")
if("x${CMAKE_CXX_COMPILER_ID}" STREQUAL "xMSVC")
set(ADDITIONAL_LIB_SEARCH_PATH_RELEASE "${FBX_SEARCH_LIB_PATH}/release/")
set(ADDITIONAL_LIB_SEARCH_PATH_DEBUG "${FBX_SEARCH_LIB_PATH}/debug/")
if (NOT DEFINED FBX_MSVC_RT_DLL OR FBX_MSVC_RT_DLL)
set(XML_SEARCH_LIB_NAMES libxml2-md.lib)
set(Z_SEARCH_LIB_NAMES zlib-md.lib)
else()
set(XML_SEARCH_LIB_NAMES libxml2-mt.lib)
set(Z_SEARCH_LIB_NAMES zlib-mt.lib)
endif()
else()
set(ADDITIONAL_LIB_SEARCH_PATH_RELEASE "")
set(ADDITIONAL_LIB_SEARCH_PATH_DEBUG "")
set(XML_SEARCH_LIB_NAMES "xml2")
set(Z_SEARCH_LIB_NAMES "z")
endif()
find_library(XML_LIB
${XML_SEARCH_LIB_NAMES}
HINTS ${ADDITIONAL_LIB_SEARCH_PATH_RELEASE})
find_library(Z_LIB
${Z_SEARCH_LIB_NAMES}
HINTS ${ADDITIONAL_LIB_SEARCH_PATH_RELEASE})
# Searches debug version also
find_library(XML_LIB_DEBUG
${XML_SEARCH_LIB_NAMES}
HINTS ${ADDITIONAL_LIB_SEARCH_PATH_DEBUG})
find_library(Z_LIB_DEBUG
${Z_SEARCH_LIB_NAMES}
HINTS ${ADDITIONAL_LIB_SEARCH_PATH_DEBUG})
# for whatever reason on apple it will need iconv as well?!
if(APPLE)
find_library(ICONV_LIB
iconv)
# no special debug search here as mac only anyway
if(NOT ICONV_LIB)
message(WARNING "FBX found but required iconv was not found!")
endif()
list(APPEND FBX_LIB ${ICONV_LIB})
list(APPEND FBX_LIB_DEBUG ${ICONV_LIB})
endif()
if(NOT XML_LIB)
message(WARNING "FBX found but required libxml2 was not found!")
endif()
if(NOT Z_LIB)
message(WARNING "FBX found but required zlib was not found!")
endif()
list(APPEND FBX_LIB ${XML_LIB} ${Z_LIB})
list(APPEND FBX_LIB_DEBUG ${XML_LIB_DEBUG} ${Z_LIB_DEBUG})
endif()
set(${_OUT_FBX_LIBRARIES} ${FBX_LIB} PARENT_SCOPE)
set(${_OUT_FBX_LIBRARIES_DEBUG} ${FBX_LIB_DEBUG} PARENT_SCOPE)
else()
message ("A Fbx SDK was found, but doesn't match your compiler settings.")
endif()
# Deduce fbx sdk version
endfunction()
###############################################################################
# Deduce Fbx sdk version
###############################################################################
function(FindFbxVersion _FBX_ROOT_DIR _OUT_FBX_VERSION)
# Opens fbxsdk_version.h in _FBX_ROOT_DIR and finds version defines.
set(fbx_version_filename "${_FBX_ROOT_DIR}include/fbxsdk/fbxsdk_version.h")
if(NOT EXISTS ${fbx_version_filename})
message(SEND_ERROR "Unable to find fbxsdk_version.h")
endif()
file(READ ${fbx_version_filename} fbx_version_file_content)
# Find version major
if(fbx_version_file_content MATCHES "FBXSDK_VERSION_MAJOR[\t ]+([0-9]+)")
set(fbx_version_file_major "${CMAKE_MATCH_1}")
endif()
# Find version minor
if(fbx_version_file_content MATCHES "FBXSDK_VERSION_MINOR[\t ]+([0-9]+)")
set(fbx_version_file_minor "${CMAKE_MATCH_1}")
endif()
# Find version patch
if(fbx_version_file_content MATCHES "FBXSDK_VERSION_POINT[\t ]+([0-9]+)")
set(fbx_version_file_patch "${CMAKE_MATCH_1}")
endif()
if (DEFINED fbx_version_file_major AND
DEFINED fbx_version_file_minor AND
DEFINED fbx_version_file_patch)
set(${_OUT_FBX_VERSION} ${fbx_version_file_major}.${fbx_version_file_minor}.${fbx_version_file_patch} PARENT_SCOPE)
else()
message(SEND_ERROR "Unable to deduce Fbx version for root dir ${_FBX_ROOT_DIR}")
set(${_OUT_FBX_VERSION} "unknown" PARENT_SCOPE)
endif()
endfunction()
###############################################################################
# Main find package function
###############################################################################
# Tries to find FBX SDK path
set(FBX_SEARCH_PATHS
"${FBX_DIR}"
"$ENV{FBX_DIR}"
"$ENV{ProgramW6432}/Autodesk/FBX/FBX SDK/*/"
"$ENV{PROGRAMFILES}/Autodesk/FBX/FBX SDK/*/"
"/Applications/Autodesk/FBX SDK/*/")
find_path(FBX_INCLUDE_DIR
NAMES "include/fbxsdk.h"
PATHS ${FBX_SEARCH_PATHS})
if(FBX_INCLUDE_DIR)
# Deduce SDK root directory.
set(FBX_ROOT_DIR "${FBX_INCLUDE_DIR}/")
# Fills CMake standard variables
set(FBX_INCLUDE_DIRS "${FBX_INCLUDE_DIR}/include")
# Searches libraries according to the current compiler
FindFbxLibrariesGeneric(${FBX_ROOT_DIR} FBX_LIBRARIES FBX_LIBRARIES_DEBUG)
endif()
# Handles find_package arguments and set FBX_FOUND to TRUE if all listed variables and version are valid.
include(FindPackageHandleStandardArgs)
find_package_handle_standard_args(Fbx
FOUND_VAR FBX_FOUND
REQUIRED_VARS FBX_LIBRARIES FBX_INCLUDE_DIRS
VERSION_VAR PATH_VERSION)
# Warn about how this script can fail to find the newest version.
if(NOT FBX_FOUND)
message("-- Note that the FindFbx.cmake script can fail to find the newest Fbx sdk if there are multiple ones installed. Please set \"FBX_DIR\" environment or cmake variable to choose a specific version/location.")
endif()
@@ -0,0 +1,37 @@
# Setup packages informations.
#-----------------------------
# Prepares installation
install(DIRECTORY "${PROJECT_SOURCE_DIR}/include" DESTINATION ".")
# Prepares packing
set(CPACK_PACKAGE_VERSION_MAJOR ${OZZ_VERSION_MAJOR})
set(CPACK_PACKAGE_VERSION_MINOR ${OZZ_VERSION_MINOR})
set(CPACK_PACKAGE_VERSION_PATCH ${OZZ_VERSION_PATCH})
set(CPACK_PACKAGE_VENDOR "Guillaume Blanc")
set(CPACK_PACKAGE_DESCRIPTION_SUMMARY "Ozz run-time animation library and tools. http://github.com/guillaumeblanc/ozz-animation")
#set(CPACK_PACKAGE_ICON )
set(CPACK_INCLUDE_TOPLEVEL_DIRECTORY 0)
set(CPACK_RESOURCE_FILE_LICENSE "${PROJECT_SOURCE_DIR}/LICENSE.md")
set(CPACK_SOURCE_IGNORE_FILES
"/build/" # Out-of-source build directory.
"/Testing/" # CDash generated files.
"/\\\\.git/"
".*\\\\.kdev4"
".*~")
set(CPACK_NSIS_MENU_LINKS
"http://github.com/guillaumeblanc/ozz-animation;Ozz home"
"bin/samples;Samples"
"bin/tools;Tools")
# Defines local variables used for packaging
STRING(SUBSTRING ${CMAKE_SYSTEM_NAME} 0 3 _PACKAGE_OS)
if("${CMAKE_SIZEOF_VOID_P}" EQUAL "4")
set(_PACKAGE_BITS "32")
else()
set(_PACKAGE_BITS "64")
endif()
set(_PACKAGE_COMILER ${CMAKE_CXX_COMPILER_ID})
set(_PACKAGE_VERSION "${CPACK_PACKAGE_VERSION_MAJOR}.${CPACK_PACKAGE_VERSION_MINOR}.${CPACK_PACKAGE_VERSION_PATCH}")
set(CPACK_PACKAGE_FILE_NAME "${CMAKE_PROJECT_NAME}-${_PACKAGE_VERSION}-${_PACKAGE_OS}${_PACKAGE_BITS}-${_PACKAGE_COMILER}")
include(CPack)
@@ -0,0 +1,205 @@
#!/usr/bin/python
#----------------------------------------------------------------------------#
# #
# ozz-animation is hosted at http://github.com/guillaumeblanc/ozz-animation #
# and distributed under the MIT License (MIT). #
# #
# Copyright (c) Guillaume Blanc #
# #
# Permission is hereby granted, free of charge, to any person obtaining a #
# copy of this software and associated documentation files (the "Software"), #
# to deal in the Software without restriction, including without limitation #
# the rights to use, copy, modify, merge, publish, distribute, sublicense, #
# and/or sell copies of the Software, and to permit persons to whom the #
# Software is 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 Software. #
# #
# THE SOFTWARE IS 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 SOFTWARE OR THE USE OR OTHER #
# DEALINGS IN THE SOFTWARE. #
# #
#----------------------------------------------------------------------------#
import os, glob
import sys
import itertools
import string
import re
import time
def recurse_files(_folder, _filter):
# Iterate files.
for i in glob.iglob(os.path.join(_folder, _filter)):
yield i
# Iterate folders...
for i in glob.iglob(os.path.join(_folder, '*/')):
#... and recurse them.
for j in recurse_files(i, _filter):
if j.find('\\extern\\') == -1 and j.find('/extern/') == -1 and j.find('\\build\\') == -1 and j.find('/build/') == -1 and j.find('\\src_fused\\') == -1 and j.find('/src_fused/') == -1:
yield j
license_text = "\
//----------------------------------------------------------------------------//\n\
// //\n\
// ozz-animation is hosted at http://github.com/guillaumeblanc/ozz-animation //\n\
// and distributed under the MIT License (MIT). //\n\
// //\n\
// Copyright (c) Guillaume Blanc //\n\
// //\n\
// Permission is hereby granted, free of charge, to any person obtaining a //\n\
// copy of this software and associated documentation files (the \"Software\"), //\n\
// to deal in the Software without restriction, including without limitation //\n\
// the rights to use, copy, modify, merge, publish, distribute, sublicense, //\n\
// and/or sell copies of the Software, and to permit persons to whom the //\n\
// Software is furnished to do so, subject to the following conditions: //\n\
// //\n\
// The above copyright notice and this permission notice shall be included in //\n\
// all copies or substantial portions of the Software. //\n\
// //\n\
// THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR //\n\
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, //\n\
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL //\n\
// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER //\n\
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING //\n\
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER //\n\
// DEALINGS IN THE SOFTWARE. //\n\
// //\n\
//----------------------------------------------------------------------------//\n\
\n\
#"
def process_file(_file, _is_h):
# Read
fr = open(_file, 'rt')
if fr == None:
print "Failed to read file " + _file
return False
text = fr.read();
fr.close()
# Prepares output
output = ""
modified = False;
# Test for a valid license
find_license = string.find(text, license_text)
if find_license == -1:
# Replaces license up to the first '#'
first_define = string.find(text, '#')
if first_define != -1:
output = license_text + text[first_define + 1:]
else:
output = license_text + text
modified = True
else:
output = text
# '#' must be found as it is part of the license
first_define = string.find(output, '#')
if _is_h:
# Test for a valid #define GUARD
# Removes pragma once
pragma_once = '#pragma once'
pragma_found = string.find(output[first_define:], pragma_once)
if pragma_found == 0:
output = output[:first_define] + output[first_define + len(pragma_once):]
modified = True
# Prepares #define GUARD
guard = string.upper(_file)
to_replace = ['/', '\\', '.', '-']
for i in to_replace:
guard = string.replace(guard, i, '_')
to_remove = ['INCLUDE_', 'SRC_']
for i in to_remove:
guard = string.replace(guard, i, '')
guard = 'OZZ_' + guard + '_'
guard = re.sub('_+', '_', guard)
header = '#ifndef ' + guard + '\n' + '#define ' + guard + '\n'
footer = '#endif // ' + guard + '\n'
# Test for a valid header/footer
found_match = re.search('^#ifndef (?P<found_guard>.+)\n^#define (?P=found_guard)\n(.*\n)*^#endif // (?P=found_guard)',
output[first_define:],
re.MULTILINE);
if found_match == None:
output = output[:first_define] + header + output[first_define:]
if not output.endswith('\n'):
output += '\n'
output += footer;
modified = True
elif found_match.group('found_guard') != guard:
output = string.replace(output, found_match.group('found_guard'), guard)
modified = True
# Needs at least 1 \n
if not output.endswith('\n'):
output += '\n'
# remove \n after guard begin
guard_pos = output.find(header) + len(header) - 1
if not output.startswith('\n\n', guard_pos):
output = output[:guard_pos] + '\n' + output[guard_pos:]
modified = True
while output.startswith('\n\n\n', guard_pos):
output = output[:guard_pos] + output[guard_pos+1:]
modified = True
# remove \n before guard end
guard_pos = output.find(footer)
while output.endswith('\n\n', 0, guard_pos):
output = output[:guard_pos-1] + output[guard_pos:]
guard_pos = output.find(footer)
modified = True
# must end with a single \n
if not output.endswith('\n'):
output += '\n'
modified = True
else:
while output.endswith('\n\n'):
output = output[:len(output) - 1]
modified = True
# Write
if modified:
fw = open(_file, 'wt')
if fw == None:
print "Failed to write file " + _file
modified = False
fw.write(output)
fw.close()
print _file + ' modified'
return modified
def process_h(_file):
return process_file(_file, True)
def process_cc(_file):
return process_file(_file, False)
def main():
# Process .h
for i in recurse_files('../../', '*.h'):
process_h(i)
# Process .cc
for i in recurse_files('../../', '*.cc'):
process_cc(i)
#
print 'Terminated'
while 1:
time.sleep(10)
main()
+10
View File
@@ -0,0 +1,10 @@
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
<html>
<head>
<title>ozz-animation build dashboard</title>
<meta http-equiv="REFRESH" content="0;url=http://guillaumeblanc.github.io/ozz-animation/documentation/dashboard/">
</head>
<body>
Redirecting... Please wait.
</body>
</html>
+10
View File
@@ -0,0 +1,10 @@
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
<html>
<head>
<title>ozz-animation documentation</title>
<meta http-equiv="REFRESH" content="0;url=http://guillaumeblanc.github.io/ozz-animation/">
</head>
<body>
Redirecting... Please wait.
</body>
</html>
+108
View File
@@ -0,0 +1,108 @@
set(OpenGL_GL_PREFERENCE LEGACY)
find_package(OpenGL REQUIRED)
# Buils Win32 specific files and options
if(WIN32)
include_directories(lib/win32)
set(specific_file_list
lib/win32/platform.h
lib/win32/win32_dllmain.c
lib/win32/win32_enable.c
lib/win32/win32_fullscreen.c
lib/win32/win32_glext.c
lib/win32/win32_init.c
lib/win32/win32_joystick.c
lib/win32/win32_thread.c
lib/win32/win32_time.c
lib/win32/win32_window.c)
if(MSYS OR MINGW)
# Disables warnings in glfw.
set_source_files_properties(${specific_file_list} PROPERTIES COMPILE_FLAGS "-Wno-unknown-pragmas")
endif()
endif()
# Samples requires X11 package on linux.
if(UNIX AND NOT APPLE)
find_package(X11)
if(X11_FOUND)
include_directories(lib/x11)
include_directories(${X11_INCLUDE_DIR})
set(specific_file_list
lib/x11/platform.h
lib/x11/x11_enable.c
lib/x11/x11_fullscreen.c
lib/x11/x11_glext.c
lib/x11/x11_init.c
lib/x11/x11_joystick.c
lib/x11/x11_keysym2unicode.c
lib/x11/x11_thread.c
lib/x11/x11_time.c
lib/x11/x11_window.c)
# Needs _GLFW_HAS_GLXGETPROCADDRESSARB preprocessor definition
set_source_files_properties(${specific_file_list} PROPERTIES COMPILE_DEFINITIONS _GLFW_HAS_GLXGETPROCADDRESSARB=)
endif()
endif()
# Mac OSX
if(UNIX AND APPLE)
find_library(COCOA_FRAMEWORK Cocoa)
find_library(IOKIT_FRAMEWORK IOKit)
include_directories(lib/cocoa)
set(specific_objc_file_list
lib/cocoa/cocoa_enable.m
lib/cocoa/cocoa_fullscreen.m
lib/cocoa/cocoa_glext.m
lib/cocoa/cocoa_init.m
lib/cocoa/cocoa_joystick.m
lib/cocoa/cocoa_time.m
lib/cocoa/cocoa_window.m)
# Treats .m files as C files.
set_source_files_properties(${specific_objc_file_list} PROPERTIES LANGUAGE C)
# Disables warnings in glfw.
set_source_files_properties(${specific_objc_file_list} PROPERTIES COMPILE_FLAGS
"-Wno-deprecated-declarations -Wno-incompatible-pointer-types -Wno-implicit-function-declaration -Wno-int-conversion")
# Appends other c files
set(specific_file_list
${specific_objc_file_list}
lib/cocoa/cocoa_thread.c
lib/cocoa/platform.h)
endif()
add_library(glfw STATIC
include/GL/glfw.h
include/GL/glext.h
lib/enable.c
lib/fullscreen.c
lib/glext.c
lib/image.c
lib/init.c
lib/input.c
lib/internal.h
lib/joystick.c
lib/stream.c
lib/tga.c
lib/thread.c
lib/time.c
lib/window.c
${specific_file_list})
target_include_directories(glfw PUBLIC
$<BUILD_INTERFACE:${PROJECT_SOURCE_DIR}/extern/glfw/include>)
target_include_directories(glfw PUBLIC
$<BUILD_INTERFACE:${OPENGL_INCLUDE_DIR}>)
target_include_directories(glfw PRIVATE
$<BUILD_INTERFACE:${PROJECT_SOURCE_DIR}/extern/glfw/lib>)
# Disables GL deprecation warnings on macos
target_compile_definitions(glfw PUBLIC $<$<BOOL:APPLE>:GL_SILENCE_DEPRECATION>)
target_link_libraries(glfw
${OPENGL_LIBRARIES}
${X11_LIBRARIES}
${COCOA_FRAMEWORK}
${IOKIT_FRAMEWORK})
set_target_properties(glfw
PROPERTIES FOLDER "extern")
+22
View File
@@ -0,0 +1,22 @@
Copyright (c) 2002-2006 Marcus Geelnard
Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
This software is provided 'as-is', without any express or implied
warranty. In no event will the authors be held liable for any damages
arising from the use of this software.
Permission is granted to anyone to use this software for any purpose,
including commercial applications, and to alter it and redistribute it
freely, subject to the following restrictions:
1. The origin of this software must not be misrepresented; you must not
claim that you wrote the original software. If you use this software
in a product, an acknowledgment in the product documentation would
be appreciated but is not required.
2. Altered source versions must be plainly marked as such, and must not
be misrepresented as being the original software.
3. This notice may not be removed or altered from any source
distribution.
+15
View File
@@ -0,0 +1,15 @@
URL: http://www.glfw.org/
Version: 2.8.0
(Downloaded glfw-2.8.zip
from http://www.glfw.org/download.html)
License: zlib/libpng license
License File: COPYING
Description: GLFW is a free, open source, portable library for OpenGL
application development.
Local Modifications:
- Extracted include and source files from glfw package.
- Striped from unsued files.
- Added CMakeLists.txt build file.
- Fix w4 and wall warnings.
-
File diff suppressed because it is too large Load Diff
+518
View File
@@ -0,0 +1,518 @@
/************************************************************************
* GLFW - An OpenGL framework
* API version: 2.7
* WWW: http://www.glfw.org/
*------------------------------------------------------------------------
* Copyright (c) 2002-2006 Marcus Geelnard
* Copyright (c) 2006-2010 Camilla Berglund
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would
* be appreciated but is not required.
*
* 2. Altered source versions must be plainly marked as such, and must not
* be misrepresented as being the original software.
*
* 3. This notice may not be removed or altered from any source
* distribution.
*
*************************************************************************/
#ifndef __glfw_h_
#define __glfw_h_
#ifdef __cplusplus
extern "C" {
#endif
/*************************************************************************
* Global definitions
*************************************************************************/
/* We need a NULL pointer from time to time */
#ifndef NULL
#ifdef __cplusplus
#define NULL 0
#else
#define NULL ((void *)0)
#endif
#endif /* NULL */
/* ------------------- BEGIN SYSTEM/COMPILER SPECIFIC -------------------- */
/* Please report any probles that you find with your compiler, which may
* be solved in this section! There are several compilers that I have not
* been able to test this file with yet.
*
* First: If we are we on Windows, we want a single define for it (_WIN32)
* (Note: For Cygwin the compiler flag -mwin32 should be used, but to
* make sure that things run smoothly for Cygwin users, we add __CYGWIN__
* to the list of "valid Win32 identifiers", which removes the need for
* -mwin32)
*/
#if !defined(_WIN32) && (defined(__WIN32__) || defined(WIN32) || defined(__CYGWIN__))
#define _WIN32
#endif /* _WIN32 */
/* In order for extension support to be portable, we need to define an
* OpenGL function call method. We use the keyword APIENTRY, which is
* defined for Win32. (Note: Windows also needs this for <GL/gl.h>)
*/
#ifndef APIENTRY
#ifdef _WIN32
#define APIENTRY __stdcall
#else
#define APIENTRY
#endif
#define GL_APIENTRY_DEFINED
#endif /* APIENTRY */
/* The following three defines are here solely to make some Windows-based
* <GL/gl.h> files happy. Theoretically we could include <windows.h>, but
* it has the major drawback of severely polluting our namespace.
*/
/* Under Windows, we need WINGDIAPI defined */
#if !defined(WINGDIAPI) && defined(_WIN32)
#if defined(_MSC_VER) || defined(__BORLANDC__) || defined(__POCC__)
/* Microsoft Visual C++, Borland C++ Builder and Pelles C */
#define WINGDIAPI __declspec(dllimport)
#elif defined(__LCC__)
/* LCC-Win32 */
#define WINGDIAPI __stdcall
#else
/* Others (e.g. MinGW, Cygwin) */
#define WINGDIAPI extern
#endif
#define GL_WINGDIAPI_DEFINED
#endif /* WINGDIAPI */
/* Some <GL/glu.h> files also need CALLBACK defined */
#if !defined(CALLBACK) && defined(_WIN32)
#if defined(_MSC_VER)
/* Microsoft Visual C++ */
#if (defined(_M_MRX000) || defined(_M_IX86) || defined(_M_ALPHA) || defined(_M_PPC)) && !defined(MIDL_PASS)
#define CALLBACK __stdcall
#else
#define CALLBACK
#endif
#else
/* Other Windows compilers */
#define CALLBACK __stdcall
#endif
#define GLU_CALLBACK_DEFINED
#endif /* CALLBACK */
/* Microsoft Visual C++, Borland C++ and Pelles C <GL*glu.h> needs wchar_t */
#if defined(_WIN32) && (defined(_MSC_VER) || defined(__BORLANDC__) || defined(__POCC__)) && !defined(_WCHAR_T_DEFINED)
typedef unsigned short wchar_t;
#define _WCHAR_T_DEFINED
#endif /* _WCHAR_T_DEFINED */
/* ---------------- GLFW related system specific defines ----------------- */
#if defined(_WIN32) && defined(GLFW_BUILD_DLL)
/* We are building a Win32 DLL */
#define GLFWAPI __declspec(dllexport)
#define GLFWAPIENTRY __stdcall
#define GLFWCALL __stdcall
#elif defined(_WIN32) && defined(GLFW_DLL)
/* We are calling a Win32 DLL */
#if defined(__LCC__)
#define GLFWAPI extern
#else
#define GLFWAPI __declspec(dllimport)
#endif
#define GLFWAPIENTRY __stdcall
#define GLFWCALL __stdcall
#else
/* We are either building/calling a static lib or we are non-win32 */
#define GLFWAPIENTRY
#define GLFWAPI
#define GLFWCALL
#endif
/* -------------------- END SYSTEM/COMPILER SPECIFIC --------------------- */
/* Include standard OpenGL headers: GLFW uses GL_FALSE/GL_TRUE, and it is
* convenient for the user to only have to include <GL/glfw.h>. This also
* solves the problem with Windows <GL/gl.h> and <GL/glu.h> needing some
* special defines which normally requires the user to include <windows.h>
* (which is not a nice solution for portable programs).
*/
#if defined(__APPLE_CC__)
#if defined(GLFW_INCLUDE_GL3)
#include <OpenGL/gl3.h>
#else
#define GL_GLEXT_LEGACY
#include <OpenGL/gl.h>
#endif
#ifndef GLFW_NO_GLU
#include <OpenGL/glu.h>
#endif
#else
#if defined(GLFW_INCLUDE_GL3)
#include <GL3/gl3.h>
#else
#include <GL/gl.h>
#endif
#ifndef GLFW_NO_GLU
#include <GL/glu.h>
#endif
#endif
/*************************************************************************
* GLFW version
*************************************************************************/
#define GLFW_VERSION_MAJOR 2
#define GLFW_VERSION_MINOR 7
#define GLFW_VERSION_REVISION 8
/*************************************************************************
* Input handling definitions
*************************************************************************/
/* Key and button state/action definitions */
#define GLFW_RELEASE 0
#define GLFW_PRESS 1
/* Keyboard key definitions: 8-bit ISO-8859-1 (Latin 1) encoding is used
* for printable keys (such as A-Z, 0-9 etc), and values above 256
* represent special (non-printable) keys (e.g. F1, Page Up etc).
*/
#define GLFW_KEY_UNKNOWN -1
#define GLFW_KEY_SPACE 32
#define GLFW_KEY_SPECIAL 256
#define GLFW_KEY_ESC (GLFW_KEY_SPECIAL+1)
#define GLFW_KEY_F1 (GLFW_KEY_SPECIAL+2)
#define GLFW_KEY_F2 (GLFW_KEY_SPECIAL+3)
#define GLFW_KEY_F3 (GLFW_KEY_SPECIAL+4)
#define GLFW_KEY_F4 (GLFW_KEY_SPECIAL+5)
#define GLFW_KEY_F5 (GLFW_KEY_SPECIAL+6)
#define GLFW_KEY_F6 (GLFW_KEY_SPECIAL+7)
#define GLFW_KEY_F7 (GLFW_KEY_SPECIAL+8)
#define GLFW_KEY_F8 (GLFW_KEY_SPECIAL+9)
#define GLFW_KEY_F9 (GLFW_KEY_SPECIAL+10)
#define GLFW_KEY_F10 (GLFW_KEY_SPECIAL+11)
#define GLFW_KEY_F11 (GLFW_KEY_SPECIAL+12)
#define GLFW_KEY_F12 (GLFW_KEY_SPECIAL+13)
#define GLFW_KEY_F13 (GLFW_KEY_SPECIAL+14)
#define GLFW_KEY_F14 (GLFW_KEY_SPECIAL+15)
#define GLFW_KEY_F15 (GLFW_KEY_SPECIAL+16)
#define GLFW_KEY_F16 (GLFW_KEY_SPECIAL+17)
#define GLFW_KEY_F17 (GLFW_KEY_SPECIAL+18)
#define GLFW_KEY_F18 (GLFW_KEY_SPECIAL+19)
#define GLFW_KEY_F19 (GLFW_KEY_SPECIAL+20)
#define GLFW_KEY_F20 (GLFW_KEY_SPECIAL+21)
#define GLFW_KEY_F21 (GLFW_KEY_SPECIAL+22)
#define GLFW_KEY_F22 (GLFW_KEY_SPECIAL+23)
#define GLFW_KEY_F23 (GLFW_KEY_SPECIAL+24)
#define GLFW_KEY_F24 (GLFW_KEY_SPECIAL+25)
#define GLFW_KEY_F25 (GLFW_KEY_SPECIAL+26)
#define GLFW_KEY_UP (GLFW_KEY_SPECIAL+27)
#define GLFW_KEY_DOWN (GLFW_KEY_SPECIAL+28)
#define GLFW_KEY_LEFT (GLFW_KEY_SPECIAL+29)
#define GLFW_KEY_RIGHT (GLFW_KEY_SPECIAL+30)
#define GLFW_KEY_LSHIFT (GLFW_KEY_SPECIAL+31)
#define GLFW_KEY_RSHIFT (GLFW_KEY_SPECIAL+32)
#define GLFW_KEY_LCTRL (GLFW_KEY_SPECIAL+33)
#define GLFW_KEY_RCTRL (GLFW_KEY_SPECIAL+34)
#define GLFW_KEY_LALT (GLFW_KEY_SPECIAL+35)
#define GLFW_KEY_RALT (GLFW_KEY_SPECIAL+36)
#define GLFW_KEY_TAB (GLFW_KEY_SPECIAL+37)
#define GLFW_KEY_ENTER (GLFW_KEY_SPECIAL+38)
#define GLFW_KEY_BACKSPACE (GLFW_KEY_SPECIAL+39)
#define GLFW_KEY_INSERT (GLFW_KEY_SPECIAL+40)
#define GLFW_KEY_DEL (GLFW_KEY_SPECIAL+41)
#define GLFW_KEY_PAGEUP (GLFW_KEY_SPECIAL+42)
#define GLFW_KEY_PAGEDOWN (GLFW_KEY_SPECIAL+43)
#define GLFW_KEY_HOME (GLFW_KEY_SPECIAL+44)
#define GLFW_KEY_END (GLFW_KEY_SPECIAL+45)
#define GLFW_KEY_KP_0 (GLFW_KEY_SPECIAL+46)
#define GLFW_KEY_KP_1 (GLFW_KEY_SPECIAL+47)
#define GLFW_KEY_KP_2 (GLFW_KEY_SPECIAL+48)
#define GLFW_KEY_KP_3 (GLFW_KEY_SPECIAL+49)
#define GLFW_KEY_KP_4 (GLFW_KEY_SPECIAL+50)
#define GLFW_KEY_KP_5 (GLFW_KEY_SPECIAL+51)
#define GLFW_KEY_KP_6 (GLFW_KEY_SPECIAL+52)
#define GLFW_KEY_KP_7 (GLFW_KEY_SPECIAL+53)
#define GLFW_KEY_KP_8 (GLFW_KEY_SPECIAL+54)
#define GLFW_KEY_KP_9 (GLFW_KEY_SPECIAL+55)
#define GLFW_KEY_KP_DIVIDE (GLFW_KEY_SPECIAL+56)
#define GLFW_KEY_KP_MULTIPLY (GLFW_KEY_SPECIAL+57)
#define GLFW_KEY_KP_SUBTRACT (GLFW_KEY_SPECIAL+58)
#define GLFW_KEY_KP_ADD (GLFW_KEY_SPECIAL+59)
#define GLFW_KEY_KP_DECIMAL (GLFW_KEY_SPECIAL+60)
#define GLFW_KEY_KP_EQUAL (GLFW_KEY_SPECIAL+61)
#define GLFW_KEY_KP_ENTER (GLFW_KEY_SPECIAL+62)
#define GLFW_KEY_KP_NUM_LOCK (GLFW_KEY_SPECIAL+63)
#define GLFW_KEY_CAPS_LOCK (GLFW_KEY_SPECIAL+64)
#define GLFW_KEY_SCROLL_LOCK (GLFW_KEY_SPECIAL+65)
#define GLFW_KEY_PAUSE (GLFW_KEY_SPECIAL+66)
#define GLFW_KEY_LSUPER (GLFW_KEY_SPECIAL+67)
#define GLFW_KEY_RSUPER (GLFW_KEY_SPECIAL+68)
#define GLFW_KEY_MENU (GLFW_KEY_SPECIAL+69)
#define GLFW_KEY_LAST GLFW_KEY_MENU
/* Mouse button definitions */
#define GLFW_MOUSE_BUTTON_1 0
#define GLFW_MOUSE_BUTTON_2 1
#define GLFW_MOUSE_BUTTON_3 2
#define GLFW_MOUSE_BUTTON_4 3
#define GLFW_MOUSE_BUTTON_5 4
#define GLFW_MOUSE_BUTTON_6 5
#define GLFW_MOUSE_BUTTON_7 6
#define GLFW_MOUSE_BUTTON_8 7
#define GLFW_MOUSE_BUTTON_LAST GLFW_MOUSE_BUTTON_8
/* Mouse button aliases */
#define GLFW_MOUSE_BUTTON_LEFT GLFW_MOUSE_BUTTON_1
#define GLFW_MOUSE_BUTTON_RIGHT GLFW_MOUSE_BUTTON_2
#define GLFW_MOUSE_BUTTON_MIDDLE GLFW_MOUSE_BUTTON_3
/* Joystick identifiers */
#define GLFW_JOYSTICK_1 0
#define GLFW_JOYSTICK_2 1
#define GLFW_JOYSTICK_3 2
#define GLFW_JOYSTICK_4 3
#define GLFW_JOYSTICK_5 4
#define GLFW_JOYSTICK_6 5
#define GLFW_JOYSTICK_7 6
#define GLFW_JOYSTICK_8 7
#define GLFW_JOYSTICK_9 8
#define GLFW_JOYSTICK_10 9
#define GLFW_JOYSTICK_11 10
#define GLFW_JOYSTICK_12 11
#define GLFW_JOYSTICK_13 12
#define GLFW_JOYSTICK_14 13
#define GLFW_JOYSTICK_15 14
#define GLFW_JOYSTICK_16 15
#define GLFW_JOYSTICK_LAST GLFW_JOYSTICK_16
/*************************************************************************
* Other definitions
*************************************************************************/
/* glfwOpenWindow modes */
#define GLFW_WINDOW 0x00010001
#define GLFW_FULLSCREEN 0x00010002
/* glfwGetWindowParam tokens */
#define GLFW_OPENED 0x00020001
#define GLFW_ACTIVE 0x00020002
#define GLFW_ICONIFIED 0x00020003
#define GLFW_ACCELERATED 0x00020004
#define GLFW_RED_BITS 0x00020005
#define GLFW_GREEN_BITS 0x00020006
#define GLFW_BLUE_BITS 0x00020007
#define GLFW_ALPHA_BITS 0x00020008
#define GLFW_DEPTH_BITS 0x00020009
#define GLFW_STENCIL_BITS 0x0002000A
/* The following constants are used for both glfwGetWindowParam
* and glfwOpenWindowHint
*/
#define GLFW_REFRESH_RATE 0x0002000B
#define GLFW_ACCUM_RED_BITS 0x0002000C
#define GLFW_ACCUM_GREEN_BITS 0x0002000D
#define GLFW_ACCUM_BLUE_BITS 0x0002000E
#define GLFW_ACCUM_ALPHA_BITS 0x0002000F
#define GLFW_AUX_BUFFERS 0x00020010
#define GLFW_STEREO 0x00020011
#define GLFW_WINDOW_NO_RESIZE 0x00020012
#define GLFW_FSAA_SAMPLES 0x00020013
#define GLFW_OPENGL_VERSION_MAJOR 0x00020014
#define GLFW_OPENGL_VERSION_MINOR 0x00020015
#define GLFW_OPENGL_FORWARD_COMPAT 0x00020016
#define GLFW_OPENGL_DEBUG_CONTEXT 0x00020017
#define GLFW_OPENGL_PROFILE 0x00020018
/* GLFW_OPENGL_PROFILE tokens */
#define GLFW_OPENGL_CORE_PROFILE 0x00050001
#define GLFW_OPENGL_COMPAT_PROFILE 0x00050002
/* glfwEnable/glfwDisable tokens */
#define GLFW_MOUSE_CURSOR 0x00030001
#define GLFW_STICKY_KEYS 0x00030002
#define GLFW_STICKY_MOUSE_BUTTONS 0x00030003
#define GLFW_SYSTEM_KEYS 0x00030004
#define GLFW_KEY_REPEAT 0x00030005
#define GLFW_AUTO_POLL_EVENTS 0x00030006
/* glfwWaitThread wait modes */
#define GLFW_WAIT 0x00040001
#define GLFW_NOWAIT 0x00040002
/* glfwGetJoystickParam tokens */
#define GLFW_PRESENT 0x00050001
#define GLFW_AXES 0x00050002
#define GLFW_BUTTONS 0x00050003
/* glfwReadImage/glfwLoadTexture2D flags */
#define GLFW_NO_RESCALE_BIT 0x00000001 /* Only for glfwReadImage */
#define GLFW_ORIGIN_UL_BIT 0x00000002
#define GLFW_BUILD_MIPMAPS_BIT 0x00000004 /* Only for glfwLoadTexture2D */
#define GLFW_ALPHA_MAP_BIT 0x00000008
/* Time spans longer than this (seconds) are considered to be infinity */
#define GLFW_INFINITY 100000.0
/*************************************************************************
* Typedefs
*************************************************************************/
/* The video mode structure used by glfwGetVideoModes() */
typedef struct {
int Width, Height;
int RedBits, BlueBits, GreenBits;
} GLFWvidmode;
/* Image/texture information */
typedef struct {
int Width, Height;
int Format;
int BytesPerPixel;
unsigned char *Data;
} GLFWimage;
/* Thread ID */
typedef int GLFWthread;
/* Mutex object */
typedef void * GLFWmutex;
/* Condition variable object */
typedef void * GLFWcond;
/* Function pointer types */
typedef void (GLFWCALL * GLFWwindowsizefun)(int,int);
typedef int (GLFWCALL * GLFWwindowclosefun)(void);
typedef void (GLFWCALL * GLFWwindowrefreshfun)(void);
typedef void (GLFWCALL * GLFWmousebuttonfun)(int,int);
typedef void (GLFWCALL * GLFWmouseposfun)(int,int);
typedef void (GLFWCALL * GLFWmousewheelfun)(int);
typedef void (GLFWCALL * GLFWkeyfun)(int,int);
typedef void (GLFWCALL * GLFWcharfun)(int,int);
typedef void (GLFWCALL * GLFWthreadfun)(void *);
/*************************************************************************
* Prototypes
*************************************************************************/
/* GLFW initialization, termination and version querying */
GLFWAPI int GLFWAPIENTRY glfwInit( void );
GLFWAPI void GLFWAPIENTRY glfwTerminate( void );
GLFWAPI void GLFWAPIENTRY glfwGetVersion( int *major, int *minor, int *rev );
/* Window handling */
GLFWAPI int GLFWAPIENTRY glfwOpenWindow( int width, int height, int redbits, int greenbits, int bluebits, int alphabits, int depthbits, int stencilbits, int mode );
GLFWAPI void GLFWAPIENTRY glfwOpenWindowHint( int target, int hint );
GLFWAPI void GLFWAPIENTRY glfwCloseWindow( void );
GLFWAPI void GLFWAPIENTRY glfwSetWindowTitle( const char *title );
GLFWAPI void GLFWAPIENTRY glfwGetWindowSize( int *width, int *height );
GLFWAPI void GLFWAPIENTRY glfwSetWindowSize( int width, int height );
GLFWAPI void GLFWAPIENTRY glfwSetWindowPos( int x, int y );
GLFWAPI void GLFWAPIENTRY glfwIconifyWindow( void );
GLFWAPI void GLFWAPIENTRY glfwRestoreWindow( void );
GLFWAPI void GLFWAPIENTRY glfwSwapBuffers( void );
GLFWAPI void GLFWAPIENTRY glfwSwapInterval( int interval );
GLFWAPI int GLFWAPIENTRY glfwGetWindowParam( int param );
GLFWAPI void GLFWAPIENTRY glfwSetWindowSizeCallback( GLFWwindowsizefun cbfun );
GLFWAPI void GLFWAPIENTRY glfwSetWindowCloseCallback( GLFWwindowclosefun cbfun );
GLFWAPI void GLFWAPIENTRY glfwSetWindowRefreshCallback( GLFWwindowrefreshfun cbfun );
/* Video mode functions */
GLFWAPI int GLFWAPIENTRY glfwGetVideoModes( GLFWvidmode *list, int maxcount );
GLFWAPI void GLFWAPIENTRY glfwGetDesktopMode( GLFWvidmode *mode );
/* Input handling */
GLFWAPI void GLFWAPIENTRY glfwPollEvents( void );
GLFWAPI void GLFWAPIENTRY glfwWaitEvents( void );
GLFWAPI int GLFWAPIENTRY glfwGetKey( int key );
GLFWAPI int GLFWAPIENTRY glfwGetMouseButton( int button );
GLFWAPI void GLFWAPIENTRY glfwGetMousePos( int *xpos, int *ypos );
GLFWAPI void GLFWAPIENTRY glfwSetMousePos( int xpos, int ypos );
GLFWAPI int GLFWAPIENTRY glfwGetMouseWheel( void );
GLFWAPI void GLFWAPIENTRY glfwSetMouseWheel( int pos );
GLFWAPI void GLFWAPIENTRY glfwSetKeyCallback( GLFWkeyfun cbfun );
GLFWAPI void GLFWAPIENTRY glfwSetCharCallback( GLFWcharfun cbfun );
GLFWAPI void GLFWAPIENTRY glfwSetMouseButtonCallback( GLFWmousebuttonfun cbfun );
GLFWAPI void GLFWAPIENTRY glfwSetMousePosCallback( GLFWmouseposfun cbfun );
GLFWAPI void GLFWAPIENTRY glfwSetMouseWheelCallback( GLFWmousewheelfun cbfun );
/* Joystick input */
GLFWAPI int GLFWAPIENTRY glfwGetJoystickParam( int joy, int param );
GLFWAPI int GLFWAPIENTRY glfwGetJoystickPos( int joy, float *pos, int numaxes );
GLFWAPI int GLFWAPIENTRY glfwGetJoystickButtons( int joy, unsigned char *buttons, int numbuttons );
/* Time */
GLFWAPI double GLFWAPIENTRY glfwGetTime( void );
GLFWAPI void GLFWAPIENTRY glfwSetTime( double time );
GLFWAPI void GLFWAPIENTRY glfwSleep( double time );
/* Extension support */
GLFWAPI int GLFWAPIENTRY glfwExtensionSupported( const char *extension );
GLFWAPI void* GLFWAPIENTRY glfwGetProcAddress( const char *procname );
GLFWAPI void GLFWAPIENTRY glfwGetGLVersion( int *major, int *minor, int *rev );
/* Threading support */
GLFWAPI GLFWthread GLFWAPIENTRY glfwCreateThread( GLFWthreadfun fun, void *arg );
GLFWAPI void GLFWAPIENTRY glfwDestroyThread( GLFWthread ID );
GLFWAPI int GLFWAPIENTRY glfwWaitThread( GLFWthread ID, int waitmode );
GLFWAPI GLFWthread GLFWAPIENTRY glfwGetThreadID( void );
GLFWAPI GLFWmutex GLFWAPIENTRY glfwCreateMutex( void );
GLFWAPI void GLFWAPIENTRY glfwDestroyMutex( GLFWmutex mutex );
GLFWAPI void GLFWAPIENTRY glfwLockMutex( GLFWmutex mutex );
GLFWAPI void GLFWAPIENTRY glfwUnlockMutex( GLFWmutex mutex );
GLFWAPI GLFWcond GLFWAPIENTRY glfwCreateCond( void );
GLFWAPI void GLFWAPIENTRY glfwDestroyCond( GLFWcond cond );
GLFWAPI void GLFWAPIENTRY glfwWaitCond( GLFWcond cond, GLFWmutex mutex, double timeout );
GLFWAPI void GLFWAPIENTRY glfwSignalCond( GLFWcond cond );
GLFWAPI void GLFWAPIENTRY glfwBroadcastCond( GLFWcond cond );
GLFWAPI int GLFWAPIENTRY glfwGetNumberOfProcessors( void );
/* Enable/disable functions */
GLFWAPI void GLFWAPIENTRY glfwEnable( int token );
GLFWAPI void GLFWAPIENTRY glfwDisable( int token );
/* Image/texture I/O support */
GLFWAPI int GLFWAPIENTRY glfwReadImage( const char *name, GLFWimage *img, int flags );
GLFWAPI int GLFWAPIENTRY glfwReadMemoryImage( const void *data, long size, GLFWimage *img, int flags );
GLFWAPI void GLFWAPIENTRY glfwFreeImage( GLFWimage *img );
GLFWAPI int GLFWAPIENTRY glfwLoadTexture2D( const char *name, int flags );
GLFWAPI int GLFWAPIENTRY glfwLoadMemoryTexture2D( const void *data, long size, int flags );
GLFWAPI int GLFWAPIENTRY glfwLoadTextureImage2D( GLFWimage *img, int flags );
#ifdef __cplusplus
}
#endif
#endif /* __glfw_h_ */
@@ -0,0 +1,51 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Cocoa/NSOpenGL
// API Version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2009-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
//************************************************************************
//**** Platform implementation functions ****
//************************************************************************
//========================================================================
// Enable and disable system keys
//========================================================================
void _glfwPlatformEnableSystemKeys( void )
{
// This is checked in macosx_window.m; we take no action here
}
void _glfwPlatformDisableSystemKeys( void )
{
// This is checked in macosx_window.m; we take no action here
// I don't think it's really possible to disable stuff like Exposé
// except in full-screen mode.
}
@@ -0,0 +1,104 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Cocoa/NSOpenGL
// API Version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2009-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
//========================================================================
// Check whether the display mode should be included in enumeration
//========================================================================
static BOOL modeIsGood( NSDictionary *mode )
{
// This is a bit controversial, if you've got something other than an
// LCD computer monitor as an output device you might not want these
// checks. You might also want to reject modes which are interlaced,
// or TV out. There is no one-size-fits-all policy that can work here.
// This seems like a decent compromise, but certain applications may
// wish to patch this...
return [[mode objectForKey:(id)kCGDisplayBitsPerPixel] intValue] >= 15 &&
[mode objectForKey:(id)kCGDisplayModeIsSafeForHardware] != nil &&
[mode objectForKey:(id)kCGDisplayModeIsStretched] == nil;
}
//========================================================================
// Convert Core Graphics display mode to GLFW video mode
//========================================================================
static GLFWvidmode vidmodeFromCGDisplayMode( NSDictionary *mode )
{
unsigned int width = [[mode objectForKey:(id)kCGDisplayWidth] unsignedIntValue];
unsigned int height = [[mode objectForKey:(id)kCGDisplayHeight] unsignedIntValue];
unsigned int bps = [[mode objectForKey:(id)kCGDisplayBitsPerSample] unsignedIntValue];
GLFWvidmode result;
result.Width = width;
result.Height = height;
result.RedBits = bps;
result.GreenBits = bps;
result.BlueBits = bps;
return result;
}
//************************************************************************
//**** Platform implementation functions ****
//************************************************************************
//========================================================================
// Get a list of available video modes
//========================================================================
int _glfwPlatformGetVideoModes( GLFWvidmode *list, int maxcount )
{
NSArray *modes = (NSArray *)CGDisplayAvailableModes( CGMainDisplayID() );
unsigned int i, j = 0, n = [modes count];
for( i = 0; i < n && j < (unsigned)maxcount; i++ )
{
NSDictionary *mode = [modes objectAtIndex:i];
if( modeIsGood( mode ) )
{
list[j++] = vidmodeFromCGDisplayMode( mode );
}
}
return j;
}
//========================================================================
// Get the desktop video mode
//========================================================================
void _glfwPlatformGetDesktopMode( GLFWvidmode *mode )
{
*mode = vidmodeFromCGDisplayMode( CGDisplayCurrentMode( CGMainDisplayID() ) );
}
@@ -0,0 +1,64 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Cocoa/NSOpenGL
// API Version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2009-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
//************************************************************************
//**** Platform implementation functions ****
//************************************************************************
//========================================================================
// Check if an OpenGL extension is available at runtime
//========================================================================
int _glfwPlatformExtensionSupported( const char *extension )
{
// There are no AGL, CGL or NSGL extensions.
return GL_FALSE;
}
//========================================================================
// Get the function pointer to an OpenGL function
//========================================================================
void * _glfwPlatformGetProcAddress( const char *procname )
{
CFStringRef symbolName = CFStringCreateWithCString( kCFAllocatorDefault,
procname,
kCFStringEncodingASCII );
void *symbol = CFBundleGetFunctionPointerForName( _glfwLibrary.OpenGLFramework,
symbolName );
CFRelease( symbolName );
return symbol;
}
@@ -0,0 +1,195 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Cocoa/NSOpenGL
// API Version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2009-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include <sys/param.h>
#include "internal.h"
@interface GLFWThread : NSThread
@end
@implementation GLFWThread
- (void)main
{
}
@end
//========================================================================
// Change to our application bundle's resources directory, if present
//========================================================================
static void changeToResourcesDirectory( void )
{
char resourcesPath[MAXPATHLEN];
CFBundleRef bundle = CFBundleGetMainBundle();
if( !bundle )
return;
CFURLRef resourcesURL = CFBundleCopyResourcesDirectoryURL( bundle );
CFStringRef last = CFURLCopyLastPathComponent( resourcesURL );
if( CFStringCompare( CFSTR( "Resources" ), last, 0 ) != kCFCompareEqualTo )
{
CFRelease( last );
CFRelease( resourcesURL );
return;
}
CFRelease( last );
if( !CFURLGetFileSystemRepresentation( resourcesURL,
true,
(UInt8*) resourcesPath,
MAXPATHLEN) )
{
CFRelease( resourcesURL );
return;
}
CFRelease( resourcesURL );
chdir( resourcesPath );
}
//========================================================================
// Terminate GLFW when exiting application
//========================================================================
static void glfw_atexit( void )
{
glfwTerminate();
}
//========================================================================
// Initialize GLFW thread package
//========================================================================
static void initThreads( void )
{
// Initialize critical section handle
(void) pthread_mutex_init( &_glfwThrd.CriticalSection, NULL );
// The first thread (the main thread) has ID 0
_glfwThrd.NextID = 0;
// Fill out information about the main thread (this thread)
_glfwThrd.First.ID = _glfwThrd.NextID ++;
_glfwThrd.First.Function = NULL;
_glfwThrd.First.PosixID = pthread_self();
_glfwThrd.First.Previous = NULL;
_glfwThrd.First.Next = NULL;
}
//************************************************************************
//**** Platform implementation functions ****
//************************************************************************
//========================================================================
// Initialize the GLFW library
//========================================================================
int _glfwPlatformInit( void )
{
_glfwLibrary.autoreleasePool = [[NSAutoreleasePool alloc] init];
_glfwLibrary.OpenGLFramework =
CFBundleGetBundleWithIdentifier( CFSTR( "com.apple.opengl" ) );
if( _glfwLibrary.OpenGLFramework == NULL )
{
return GL_FALSE;
}
GLFWThread* thread = [[GLFWThread alloc] init];
[thread start];
[thread release];
changeToResourcesDirectory();
_glfwPlatformGetDesktopMode( &_glfwLibrary.desktopMode );
// Install atexit routine
atexit( glfw_atexit );
initThreads();
_glfwInitTimer();
_glfwInitJoysticks();
_glfwLibrary.eventSource = CGEventSourceCreate( kCGEventSourceStateHIDSystemState );
if( !_glfwLibrary.eventSource )
{
return GL_FALSE;
}
CGEventSourceSetLocalEventsSuppressionInterval( _glfwLibrary.eventSource,
0.0 );
_glfwPlatformSetTime( 0.0 );
return GL_TRUE;
}
//========================================================================
// Close window, if open, and shut down GLFW
//========================================================================
int _glfwPlatformTerminate( void )
{
if( pthread_self() != _glfwThrd.First.PosixID )
{
return GL_FALSE;
}
glfwCloseWindow();
// TODO: Kill all non-main threads?
// TODO: Probably other cleanup
if( _glfwLibrary.eventSource )
{
CFRelease( _glfwLibrary.eventSource );
_glfwLibrary.eventSource = NULL;
}
_glfwTerminateJoysticks();
[_glfwLibrary.autoreleasePool release];
_glfwLibrary.autoreleasePool = nil;
return GL_TRUE;
}
@@ -0,0 +1,648 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Cocoa/NSOpenGL
// API Version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2009-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
#include <unistd.h>
#include <ctype.h>
#include <mach/mach.h>
#include <mach/mach_error.h>
#include <CoreFoundation/CoreFoundation.h>
#include <IOKit/IOKitLib.h>
#include <IOKit/IOCFPlugIn.h>
#include <IOKit/hid/IOHIDLib.h>
#include <IOKit/hid/IOHIDKeys.h>
#include <Kernel/IOKit/hidsystem/IOHIDUsageTables.h>
//------------------------------------------------------------------------
// Joystick state
//------------------------------------------------------------------------
typedef struct
{
int present;
char product[256];
IOHIDDeviceInterface** interface;
int numAxes;
int numButtons;
int numHats;
CFMutableArrayRef axes;
CFMutableArrayRef buttons;
CFMutableArrayRef hats;
} _glfwJoystick;
static _glfwJoystick _glfwJoysticks[GLFW_JOYSTICK_LAST + 1];
typedef struct
{
IOHIDElementCookie cookie;
long value;
long min;
long max;
long minReport;
long maxReport;
} _glfwJoystickElement;
void GetElementsCFArrayHandler( const void* value, void* parameter );
//========================================================================
// Adds an element to the specified joystick
//========================================================================
static void addJoystickElement( _glfwJoystick* joystick, CFTypeRef refElement )
{
long elementType, usagePage, usage;
CFTypeRef refElementType, refUsagePage, refUsage;
refElementType = CFDictionaryGetValue( refElement, CFSTR( kIOHIDElementTypeKey ) );
refUsagePage = CFDictionaryGetValue( refElement, CFSTR( kIOHIDElementUsagePageKey ) );
refUsage = CFDictionaryGetValue( refElement, CFSTR( kIOHIDElementUsageKey ) );
CFMutableArrayRef elementsArray = NULL;
CFNumberGetValue( refElementType, kCFNumberLongType, &elementType );
CFNumberGetValue( refUsagePage, kCFNumberLongType, &usagePage );
CFNumberGetValue( refUsage, kCFNumberLongType, &usage );
if( elementType == kIOHIDElementTypeInput_Axis ||
elementType == kIOHIDElementTypeInput_Button ||
elementType == kIOHIDElementTypeInput_Misc )
{
switch( usagePage ) /* only interested in kHIDPage_GenericDesktop and kHIDPage_Button */
{
case kHIDPage_GenericDesktop:
{
switch( usage )
{
case kHIDUsage_GD_X:
case kHIDUsage_GD_Y:
case kHIDUsage_GD_Z:
case kHIDUsage_GD_Rx:
case kHIDUsage_GD_Ry:
case kHIDUsage_GD_Rz:
case kHIDUsage_GD_Slider:
case kHIDUsage_GD_Dial:
case kHIDUsage_GD_Wheel:
joystick->numAxes++;
elementsArray = joystick->axes;
break;
case kHIDUsage_GD_Hatswitch:
joystick->numHats++;
elementsArray = joystick->hats;
break;
}
break;
}
case kHIDPage_Button:
joystick->numButtons++;
elementsArray = joystick->buttons;
break;
default:
break;
}
if( elementsArray )
{
long number;
CFTypeRef refType;
_glfwJoystickElement* element = (_glfwJoystickElement*) malloc( sizeof( _glfwJoystickElement ) );
CFArrayAppendValue( elementsArray, element );
refType = CFDictionaryGetValue( refElement, CFSTR( kIOHIDElementCookieKey ) );
if( refType && CFNumberGetValue( refType, kCFNumberLongType, &number ) )
{
element->cookie = (IOHIDElementCookie) number;
}
refType = CFDictionaryGetValue( refElement, CFSTR( kIOHIDElementMinKey ) );
if( refType && CFNumberGetValue( refType, kCFNumberLongType, &number ) )
{
element->minReport = element->min = number;
}
refType = CFDictionaryGetValue( refElement, CFSTR( kIOHIDElementMaxKey ) );
if( refType && CFNumberGetValue( refType, kCFNumberLongType, &number ) )
{
element->maxReport = element->max = number;
}
}
}
else
{
CFTypeRef refElementTop = CFDictionaryGetValue( refElement, CFSTR( kIOHIDElementKey ) );
if( refElementTop )
{
CFTypeID type = CFGetTypeID( refElementTop );
if( type == CFArrayGetTypeID() ) /* if element is an array */
{
CFRange range = { 0, CFArrayGetCount( refElementTop ) };
CFArrayApplyFunction( refElementTop, range, GetElementsCFArrayHandler, joystick );
}
}
}
}
//========================================================================
// Adds an element to the specified joystick
//========================================================================
void GetElementsCFArrayHandler( const void* value, void* parameter )
{
if( CFGetTypeID( value ) == CFDictionaryGetTypeID() )
{
addJoystickElement( (_glfwJoystick*) parameter, (CFTypeRef) value );
}
}
//========================================================================
// Returns the value of the specified element of the specified joystick
//========================================================================
static long getElementValue( _glfwJoystick* joystick, _glfwJoystickElement* element )
{
IOReturn result = kIOReturnSuccess;
IOHIDEventStruct hidEvent;
hidEvent.value = 0;
if( joystick && element && joystick->interface )
{
result = (*(joystick->interface))->getElementValue( joystick->interface,
element->cookie,
&hidEvent );
if( kIOReturnSuccess == result )
{
/* record min and max for auto calibration */
if( hidEvent.value < element->minReport )
{
element->minReport = hidEvent.value;
}
if( hidEvent.value > element->maxReport )
{
element->maxReport = hidEvent.value;
}
}
}
/* auto user scale */
return (long) hidEvent.value;
}
//========================================================================
// Removes the specified joystick
//========================================================================
static void removeJoystick( _glfwJoystick* joystick )
{
int i;
if( joystick->present )
{
joystick->present = GL_FALSE;
for( i = 0; i < joystick->numAxes; i++ )
{
_glfwJoystickElement* axes =
(_glfwJoystickElement*) CFArrayGetValueAtIndex( joystick->axes, i );
free( axes );
}
CFArrayRemoveAllValues( joystick->axes );
joystick->numAxes = 0;
for( i = 0; i < joystick->numButtons; i++ )
{
_glfwJoystickElement* button =
(_glfwJoystickElement*) CFArrayGetValueAtIndex( joystick->buttons, i );
free( button );
}
CFArrayRemoveAllValues( joystick->buttons );
joystick->numButtons = 0;
for( i = 0; i < joystick->numHats; i++ )
{
_glfwJoystickElement* hat =
(_glfwJoystickElement*) CFArrayGetValueAtIndex( joystick->hats, i );
free( hat );
}
CFArrayRemoveAllValues( joystick->hats );
joystick->hats = 0;
(*(joystick->interface))->close( joystick->interface );
(*(joystick->interface))->Release( joystick->interface );
joystick->interface = NULL;
}
}
//========================================================================
// Callback for user-initiated joystick removal
//========================================================================
static void removalCallback( void* target, IOReturn result, void* refcon, void* sender )
{
removeJoystick( (_glfwJoystick*) refcon );
}
//========================================================================
// Polls for joystick events and updates GFLW state
//========================================================================
static void pollJoystickEvents( void )
{
int i;
CFIndex j;
for( i = 0; i < GLFW_JOYSTICK_LAST + 1; i++ )
{
_glfwJoystick* joystick = &_glfwJoysticks[i];
if( joystick->present )
{
for( j = 0; j < joystick->numButtons; j++ )
{
_glfwJoystickElement* button =
(_glfwJoystickElement*) CFArrayGetValueAtIndex( joystick->buttons, j );
button->value = getElementValue( joystick, button );
}
for( j = 0; j < joystick->numAxes; j++ )
{
_glfwJoystickElement* axes =
(_glfwJoystickElement*) CFArrayGetValueAtIndex( joystick->axes, j );
axes->value = getElementValue( joystick, axes );
}
for( j = 0; j < joystick->numHats; j++ )
{
_glfwJoystickElement* hat =
(_glfwJoystickElement*) CFArrayGetValueAtIndex( joystick->hats, j );
hat->value = getElementValue( joystick, hat );
}
}
}
}
//************************************************************************
//**** GLFW internal functions ****
//************************************************************************
//========================================================================
// Initialize joystick interface
//========================================================================
void _glfwInitJoysticks( void )
{
int deviceCounter = 0;
IOReturn result = kIOReturnSuccess;
mach_port_t masterPort = 0;
io_iterator_t objectIterator = 0;
CFMutableDictionaryRef hidMatchDictionary = NULL;
io_object_t ioHIDDeviceObject = 0;
result = IOMasterPort( bootstrap_port, &masterPort );
hidMatchDictionary = IOServiceMatching( kIOHIDDeviceKey );
if( kIOReturnSuccess != result || !hidMatchDictionary )
{
if( hidMatchDictionary )
{
CFRelease( hidMatchDictionary );
}
return;
}
result = IOServiceGetMatchingServices( masterPort,
hidMatchDictionary,
&objectIterator );
if( result != kIOReturnSuccess )
{
return;
}
if( !objectIterator ) /* there are no joysticks */
{
return;
}
while( ( ioHIDDeviceObject = IOIteratorNext( objectIterator ) ) )
{
CFMutableDictionaryRef hidProperties = 0;
kern_return_t result;
CFTypeRef refCF = 0;
IOCFPlugInInterface** ppPlugInInterface = NULL;
HRESULT plugInResult = S_OK;
SInt32 score = 0;
long usagePage, usage;
result = IORegistryEntryCreateCFProperties( ioHIDDeviceObject,
&hidProperties,
kCFAllocatorDefault,
kNilOptions );
if( result != kIOReturnSuccess )
{
continue;
}
/* Check device type */
refCF = CFDictionaryGetValue( hidProperties, CFSTR( kIOHIDPrimaryUsagePageKey ) );
if( refCF )
{
CFNumberGetValue( refCF, kCFNumberLongType, &usagePage );
if( usagePage != kHIDPage_GenericDesktop )
{
/* We are not interested in this device */
continue;
}
}
refCF = CFDictionaryGetValue( hidProperties, CFSTR( kIOHIDPrimaryUsageKey ) );
if( refCF )
{
CFNumberGetValue( refCF, kCFNumberLongType, &usage );
if( usage != kHIDUsage_GD_Joystick &&
usage != kHIDUsage_GD_GamePad &&
usage != kHIDUsage_GD_MultiAxisController )
{
/* We are not interested in this device */
continue;
}
}
_glfwJoystick* joystick = &_glfwJoysticks[deviceCounter];
joystick->present = GL_TRUE;
result = IOCreatePlugInInterfaceForService( ioHIDDeviceObject,
kIOHIDDeviceUserClientTypeID,
kIOCFPlugInInterfaceID,
&ppPlugInInterface,
&score );
if( kIOReturnSuccess != result )
{
return;
}
plugInResult = (*ppPlugInInterface)->QueryInterface( ppPlugInInterface,
CFUUIDGetUUIDBytes( kIOHIDDeviceInterfaceID ),
(void *) &(joystick->interface) );
if( plugInResult != S_OK )
{
return;
}
(*ppPlugInInterface)->Release( ppPlugInInterface );
(*(joystick->interface))->open( joystick->interface, 0 );
(*(joystick->interface))->setRemovalCallback( joystick->interface,
removalCallback,
joystick,
joystick );
/* Get product string */
refCF = CFDictionaryGetValue( hidProperties, CFSTR( kIOHIDProductKey ) );
if( refCF )
{
CFStringGetCString( refCF,
(char*) &(joystick->product),
256,
CFStringGetSystemEncoding() );
}
joystick->numAxes = 0;
joystick->numButtons = 0;
joystick->numHats = 0;
joystick->axes = CFArrayCreateMutable( NULL, 0, NULL );
joystick->buttons = CFArrayCreateMutable( NULL, 0, NULL );
joystick->hats = CFArrayCreateMutable( NULL, 0, NULL );
CFTypeRef refTopElement = CFDictionaryGetValue( hidProperties,
CFSTR( kIOHIDElementKey ) );
CFTypeID type = CFGetTypeID( refTopElement );
if( type == CFArrayGetTypeID() )
{
CFRange range = { 0, CFArrayGetCount( refTopElement ) };
CFArrayApplyFunction( refTopElement,
range,
GetElementsCFArrayHandler,
(void*) joystick);
}
deviceCounter++;
}
}
//========================================================================
// Close all opened joystick handles
//========================================================================
void _glfwTerminateJoysticks( void )
{
int i;
for( i = 0; i < GLFW_JOYSTICK_LAST + 1; i++ )
{
_glfwJoystick* joystick = &_glfwJoysticks[i];
removeJoystick( joystick );
}
}
//************************************************************************
//**** Platform implementation functions ****
//************************************************************************
//========================================================================
// Determine joystick capabilities
//========================================================================
int _glfwPlatformGetJoystickParam( int joy, int param )
{
if( !_glfwJoysticks[joy].present )
{
// TODO: Figure out if this is an error
return GL_FALSE;
}
switch( param )
{
case GLFW_PRESENT:
return GL_TRUE;
case GLFW_AXES:
return (int) CFArrayGetCount( _glfwJoysticks[joy].axes );
case GLFW_BUTTONS:
return (int) CFArrayGetCount( _glfwJoysticks[joy].buttons ) +
((int) CFArrayGetCount( _glfwJoysticks[joy].hats )) * 4;
default:
break;
}
return GL_FALSE;
}
//========================================================================
// Get joystick axis positions
//========================================================================
int _glfwPlatformGetJoystickPos( int joy, float *pos, int numaxes )
{
int i;
if( joy < GLFW_JOYSTICK_1 || joy > GLFW_JOYSTICK_LAST )
{
return 0;
}
_glfwJoystick joystick = _glfwJoysticks[joy];
if( !joystick.present )
{
// TODO: Figure out if this is an error
return 0;
}
numaxes = numaxes < joystick.numAxes ? numaxes : joystick.numAxes;
// Update joystick state
pollJoystickEvents();
for( i = 0; i < numaxes; i++ )
{
_glfwJoystickElement* axes =
(_glfwJoystickElement*) CFArrayGetValueAtIndex( joystick.axes, i );
long readScale = axes->maxReport - axes->minReport;
if( readScale == 0 )
{
pos[i] = axes->value;
}
else
{
pos[i] = (2.0f * (axes->value - axes->minReport) / readScale) - 1.0f;
}
//printf("%ld, %ld, %ld\n", axes->value, axes->minReport, axes->maxReport);
if( i & 1 )
{
pos[i] = -pos[i];
}
}
return numaxes;
}
//========================================================================
// Get joystick button states
//========================================================================
int _glfwPlatformGetJoystickButtons( int joy, unsigned char *buttons, int numbuttons )
{
int i, j, button;
if( joy < GLFW_JOYSTICK_1 || joy > GLFW_JOYSTICK_LAST )
{
return 0;
}
_glfwJoystick joystick = _glfwJoysticks[joy];
if( !joystick.present )
{
// TODO: Figure out if this is an error
return 0;
}
// Update joystick state
pollJoystickEvents();
for( button = 0; button < numbuttons && button < joystick.numButtons; button++ )
{
_glfwJoystickElement* element = (_glfwJoystickElement*) CFArrayGetValueAtIndex( joystick.buttons, button );
buttons[button] = element->value ? GLFW_PRESS : GLFW_RELEASE;
}
// Virtual buttons - Inject data from hats
// Each hat is exposed as 4 buttons which exposes 8 directions with concurrent button presses
const int directions[9] = { 1, 3, 2, 6, 4, 12, 8, 9, 0 }; // Bit fields of button presses for each direction, including nil
for( i = 0; i < joystick.numHats; i++ )
{
_glfwJoystickElement* hat = (_glfwJoystickElement*) CFArrayGetValueAtIndex( joystick.hats, i );
int value = hat->value;
if( value < 0 || value > 8 )
{
value = 8;
}
for( j = 0; j < 4 && button < numbuttons; j++ )
{
buttons[button++] = directions[value] & (1 << j) ? GLFW_PRESS : GLFW_RELEASE;
}
}
return button;
}
@@ -0,0 +1,414 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Cocoa/NSOpenGL
// API Version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2009-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
#include <sys/time.h>
#include <sys/sysctl.h>
//************************************************************************
//**** GLFW internal functions ****
//************************************************************************
//========================================================================
// _glfwNewThread() - This is simply a "wrapper" for calling the user
// thread function.
//========================================================================
void * _glfwNewThread( void * arg )
{
GLFWthreadfun threadfun;
_GLFWthread *t;
// Get pointer to thread information for current thread
t = _glfwGetThreadPointer( glfwGetThreadID() );
if( t == NULL )
{
return 0;
}
// Get user thread function pointer
threadfun = t->Function;
// Call the user thread function
threadfun( arg );
// Remove thread from thread list
ENTER_THREAD_CRITICAL_SECTION
_glfwRemoveThread( t );
LEAVE_THREAD_CRITICAL_SECTION
// When the thread function returns, the thread will die...
return NULL;
}
//************************************************************************
//**** Platform implementation functions ****
//************************************************************************
//========================================================================
// _glfwPlatformCreateThread() - Create a new thread
//========================================================================
GLFWthread _glfwPlatformCreateThread( GLFWthreadfun fun, void *arg )
{
GLFWthread ID;
_GLFWthread *t;
int result;
// Enter critical section
ENTER_THREAD_CRITICAL_SECTION
// Create a new thread information memory area
t = (_GLFWthread *) malloc( sizeof(_GLFWthread) );
if( t == NULL )
{
// Leave critical section
LEAVE_THREAD_CRITICAL_SECTION
return -1;
}
// Get a new unique thread id
ID = _glfwThrd.NextID ++;
// Store thread information in the thread list
t->Function = fun;
t->ID = ID;
// Create thread
result = pthread_create(
&t->PosixID, // Thread handle
NULL, // Default thread attributes
_glfwNewThread, // Thread function (a wrapper function)
(void *)arg // Argument to thread is user argument
);
// Did the thread creation fail?
if( result != 0 )
{
free( (void *) t );
LEAVE_THREAD_CRITICAL_SECTION
return -1;
}
// Append thread to thread list
_glfwAppendThread( t );
// Leave critical section
LEAVE_THREAD_CRITICAL_SECTION
// Return the GLFW thread ID
return ID;
}
//========================================================================
// _glfwPlatformDestroyThread() - Kill a thread. NOTE: THIS IS A VERY
// DANGEROUS OPERATION, AND SHOULD NOT BE USED EXCEPT IN EXTREME
// SITUATIONS!
//========================================================================
void _glfwPlatformDestroyThread( GLFWthread ID )
{
_GLFWthread *t;
// Enter critical section
ENTER_THREAD_CRITICAL_SECTION
// Get thread information pointer
t = _glfwGetThreadPointer( ID );
if( t == NULL )
{
LEAVE_THREAD_CRITICAL_SECTION
return;
}
// Simply murder the process, no mercy!
pthread_kill( t->PosixID, SIGKILL );
// Remove thread from thread list
_glfwRemoveThread( t );
// Leave critical section
LEAVE_THREAD_CRITICAL_SECTION
}
//========================================================================
// _glfwPlatformWaitThread() - Wait for a thread to die
//========================================================================
int _glfwPlatformWaitThread( GLFWthread ID, int waitmode )
{
pthread_t thread;
_GLFWthread *t;
// Enter critical section
ENTER_THREAD_CRITICAL_SECTION
// Get thread information pointer
t = _glfwGetThreadPointer( ID );
// Is the thread already dead?
if( t == NULL )
{
LEAVE_THREAD_CRITICAL_SECTION
return GL_TRUE;
}
// If got this far, the thread is alive => polling returns FALSE
if( waitmode == GLFW_NOWAIT )
{
LEAVE_THREAD_CRITICAL_SECTION
return GL_FALSE;
}
// Get thread handle
thread = t->PosixID;
// Leave critical section
LEAVE_THREAD_CRITICAL_SECTION
// Wait for thread to die
(void) pthread_join( thread, NULL );
return GL_TRUE;
}
//========================================================================
// _glfwPlatformGetThreadID() - Return the thread ID for the current
// thread
//========================================================================
GLFWthread _glfwPlatformGetThreadID( void )
{
_GLFWthread *t;
GLFWthread ID = -1;
pthread_t posixID;
// Get current thread ID
posixID = pthread_self();
// Enter critical section
ENTER_THREAD_CRITICAL_SECTION
// Loop through entire list of threads to find the matching POSIX
// thread ID
for( t = &_glfwThrd.First; t != NULL; t = t->Next )
{
if( t->PosixID == posixID )
{
ID = t->ID;
break;
}
}
// Leave critical section
LEAVE_THREAD_CRITICAL_SECTION
// Return the found GLFW thread identifier
return ID;
}
//========================================================================
// _glfwPlatformCreateMutex() - Create a mutual exclusion object
//========================================================================
GLFWmutex _glfwPlatformCreateMutex( void )
{
pthread_mutex_t *mutex;
// Allocate memory for mutex
mutex = (pthread_mutex_t *) malloc( sizeof( pthread_mutex_t ) );
if( !mutex )
{
return NULL;
}
// Initialise a mutex object
(void) pthread_mutex_init( mutex, NULL );
// Cast to GLFWmutex and return
return (GLFWmutex) mutex;
}
//========================================================================
// _glfwPlatformDestroyMutex() - Destroy a mutual exclusion object
//========================================================================
void _glfwPlatformDestroyMutex( GLFWmutex mutex )
{
// Destroy the mutex object
pthread_mutex_destroy( (pthread_mutex_t *) mutex );
// Free memory for mutex object
free( (void *) mutex );
}
//========================================================================
// _glfwPlatformLockMutex() - Request access to a mutex
//========================================================================
void _glfwPlatformLockMutex( GLFWmutex mutex )
{
// Wait for mutex to be released
(void) pthread_mutex_lock( (pthread_mutex_t *) mutex );
}
//========================================================================
// _glfwPlatformUnlockMutex() - Release a mutex
//========================================================================
void _glfwPlatformUnlockMutex( GLFWmutex mutex )
{
// Release mutex
pthread_mutex_unlock( (pthread_mutex_t *) mutex );
}
//========================================================================
// _glfwPlatformCreateCond() - Create a new condition variable object
//========================================================================
GLFWcond _glfwPlatformCreateCond( void )
{
pthread_cond_t *cond;
// Allocate memory for condition variable
cond = (pthread_cond_t *) malloc( sizeof(pthread_cond_t) );
if( !cond )
{
return NULL;
}
// Initialise condition variable
(void) pthread_cond_init( cond, NULL );
// Cast to GLFWcond and return
return (GLFWcond) cond;
}
//========================================================================
// _glfwPlatformDestroyCond() - Destroy a condition variable object
//========================================================================
void _glfwPlatformDestroyCond( GLFWcond cond )
{
// Destroy the condition variable object
(void) pthread_cond_destroy( (pthread_cond_t *) cond );
// Free memory for condition variable object
free( (void *) cond );
}
//========================================================================
// _glfwPlatformWaitCond() - Wait for a condition to be raised
//========================================================================
void _glfwPlatformWaitCond( GLFWcond cond, GLFWmutex mutex,
double timeout )
{
struct timeval currenttime;
struct timespec wait;
long dt_sec, dt_usec;
// Select infinite or timed wait
if( timeout >= GLFW_INFINITY )
{
// Wait for condition (infinite wait)
(void) pthread_cond_wait( (pthread_cond_t *) cond,
(pthread_mutex_t *) mutex );
}
else
{
// Set timeout time, relatvie to current time
gettimeofday( &currenttime, NULL );
dt_sec = (long) timeout;
dt_usec = (long) ((timeout - (double)dt_sec) * 1000000.0);
wait.tv_nsec = (currenttime.tv_usec + dt_usec) * 1000L;
if( wait.tv_nsec > 1000000000L )
{
wait.tv_nsec -= 1000000000L;
dt_sec ++;
}
wait.tv_sec = currenttime.tv_sec + dt_sec;
// Wait for condition (timed wait)
(void) pthread_cond_timedwait( (pthread_cond_t *) cond,
(pthread_mutex_t *) mutex, &wait );
}
}
//========================================================================
// _glfwPlatformSignalCond() - Signal a condition to one waiting thread
//========================================================================
void _glfwPlatformSignalCond( GLFWcond cond )
{
// Signal condition
(void) pthread_cond_signal( (pthread_cond_t *) cond );
}
//========================================================================
// _glfwPlatformBroadcastCond() - Broadcast a condition to all waiting
// threads
//========================================================================
void _glfwPlatformBroadcastCond( GLFWcond cond )
{
// Broadcast condition
(void) pthread_cond_broadcast( (pthread_cond_t *) cond );
}
//========================================================================
// _glfwPlatformGetNumberOfProcessors() - Return the number of processors
// in the system.
//========================================================================
int _glfwPlatformGetNumberOfProcessors( void )
{
int n;
// Get number of processors online
_glfw_numprocessors( n );
return n;
}
@@ -0,0 +1,135 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Cocoa/NSOpenGL
// API Version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2009-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
#include <mach/mach_time.h>
#include <sys/time.h>
//========================================================================
// Return raw time
//========================================================================
static uint64_t getRawTime( void )
{
return mach_absolute_time();
}
//========================================================================
// Initialise timer
//========================================================================
void _glfwInitTimer( void )
{
mach_timebase_info_data_t info;
mach_timebase_info( &info );
_glfwLibrary.timer.resolution = (double) info.numer / ( info.denom * 1.0e9 );
_glfwLibrary.timer.base = getRawTime();
}
//************************************************************************
//**** Platform implementation functions ****
//************************************************************************
//========================================================================
// Return timer value in seconds
//========================================================================
double _glfwPlatformGetTime( void )
{
return (double) ( getRawTime() - _glfwLibrary.timer.base ) *
_glfwLibrary.timer.resolution;
}
//========================================================================
// Set timer value in seconds
//========================================================================
void _glfwPlatformSetTime( double time )
{
_glfwLibrary.timer.base = getRawTime() -
(uint64_t) ( time / _glfwLibrary.timer.resolution );
}
//========================================================================
// Put a thread to sleep for a specified amount of time
//========================================================================
void _glfwPlatformSleep( double time )
{
if( time == 0.0 )
{
sched_yield();
return;
}
struct timeval currenttime;
struct timespec wait;
pthread_mutex_t mutex;
pthread_cond_t cond;
long dt_sec, dt_usec;
// Not all pthread implementations have a pthread_sleep() function. We
// do it the portable way, using a timed wait for a condition that we
// will never signal. NOTE: The unistd functions sleep/usleep suspends
// the entire PROCESS, not a signle thread, which is why we can not
// use them to implement glfwSleep.
// Set timeout time, relatvie to current time
gettimeofday( &currenttime, NULL );
dt_sec = (long) time;
dt_usec = (long) ((time - (double)dt_sec) * 1000000.0);
wait.tv_nsec = (currenttime.tv_usec + dt_usec) * 1000L;
if( wait.tv_nsec > 1000000000L )
{
wait.tv_nsec -= 1000000000L;
dt_sec ++;
}
wait.tv_sec = currenttime.tv_sec + dt_sec;
// Initialize condition and mutex objects
pthread_mutex_init( &mutex, NULL );
pthread_cond_init( &cond, NULL );
// Do a timed wait
pthread_mutex_lock( &mutex );
pthread_cond_timedwait( &cond, &mutex, &wait );
pthread_mutex_unlock( &mutex );
// Destroy condition and mutex objects
pthread_mutex_destroy( &mutex );
pthread_cond_destroy( &cond );
}
File diff suppressed because it is too large Load Diff
+268
View File
@@ -0,0 +1,268 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Cocoa/NSOpenGL
// API Version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2009-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#ifndef _platform_h_
#define _platform_h_
// This is the Mac OS X version of GLFW
#define _GLFW_MAC_OS_X
#if defined(__OBJC__)
#import <Cocoa/Cocoa.h>
#else
#include <ApplicationServices/ApplicationServices.h>
typedef void *id;
#endif
#include <pthread.h>
#include "../../include/GL/glfw.h"
#ifndef GL_VERSION_3_0
typedef const GLubyte * (APIENTRY *PFNGLGETSTRINGIPROC) (GLenum, GLuint);
#endif /*GL_VERSION_3_0*/
//========================================================================
// GLFW platform specific types
//========================================================================
//------------------------------------------------------------------------
// Pointer length integer
//------------------------------------------------------------------------
typedef intptr_t GLFWintptr;
//------------------------------------------------------------------------
// Window structure
//------------------------------------------------------------------------
typedef struct _GLFWwin_struct _GLFWwin;
struct _GLFWwin_struct {
// ========= PLATFORM INDEPENDENT MANDATORY PART =========================
// User callback functions
GLFWwindowsizefun windowSizeCallback;
GLFWwindowclosefun windowCloseCallback;
GLFWwindowrefreshfun windowRefreshCallback;
GLFWmousebuttonfun mouseButtonCallback;
GLFWmouseposfun mousePosCallback;
GLFWmousewheelfun mouseWheelCallback;
GLFWkeyfun keyCallback;
GLFWcharfun charCallback;
// User selected window settings
int fullscreen; // Fullscreen flag
int mouseLock; // Mouse-lock flag
int autoPollEvents; // Auto polling flag
int sysKeysDisabled; // System keys disabled flag
int windowNoResize; // Resize- and maximize gadgets disabled flag
int refreshRate; // Vertical monitor refresh rate
// Window status & parameters
int opened; // Flag telling if window is opened or not
int active; // Application active flag
int iconified; // Window iconified flag
int width, height; // Window width and heigth
int accelerated; // GL_TRUE if window is HW accelerated
// Framebuffer attributes
int redBits;
int greenBits;
int blueBits;
int alphaBits;
int depthBits;
int stencilBits;
int accumRedBits;
int accumGreenBits;
int accumBlueBits;
int accumAlphaBits;
int auxBuffers;
int stereo;
int samples;
// OpenGL extensions and context attributes
int has_GL_SGIS_generate_mipmap;
int has_GL_ARB_texture_non_power_of_two;
int glMajor, glMinor, glRevision;
int glForward, glDebug, glProfile;
PFNGLGETSTRINGIPROC GetStringi;
// ========= PLATFORM SPECIFIC PART ======================================
id window;
id pixelFormat;
id context;
id delegate;
unsigned int modifierFlags;
};
GLFWGLOBAL _GLFWwin _glfwWin;
//------------------------------------------------------------------------
// Library global data
//------------------------------------------------------------------------
GLFWGLOBAL struct {
// ========= PLATFORM INDEPENDENT MANDATORY PART =========================
// Window opening hints
_GLFWhints hints;
// Initial desktop mode
GLFWvidmode desktopMode;
// ========= PLATFORM SPECIFIC PART ======================================
// Timer data
struct {
double base;
double resolution;
} timer;
// dlopen handle for dynamically-loading extension function pointers
void *OpenGLFramework;
id originalMode;
id autoreleasePool;
CGEventSourceRef eventSource;
} _glfwLibrary;
//------------------------------------------------------------------------
// User input status (some of this should go in _GLFWwin)
//------------------------------------------------------------------------
GLFWGLOBAL struct {
// ========= PLATFORM INDEPENDENT MANDATORY PART =========================
// Mouse status
int MousePosX, MousePosY;
int WheelPos;
char MouseButton[ GLFW_MOUSE_BUTTON_LAST+1 ];
// Keyboard status
char Key[ GLFW_KEY_LAST+1 ];
int LastChar;
// User selected settings
int StickyKeys;
int StickyMouseButtons;
int KeyRepeat;
// ========= PLATFORM SPECIFIC PART ======================================
double WheelPosFloating;
} _glfwInput;
//------------------------------------------------------------------------
// Thread information
//------------------------------------------------------------------------
typedef struct _GLFWthread_struct _GLFWthread;
// Thread record (one for each thread)
struct _GLFWthread_struct {
// Pointer to previous and next threads in linked list
_GLFWthread *Previous, *Next;
// GLFW user side thread information
GLFWthread ID;
GLFWthreadfun Function;
// System side thread information
pthread_t PosixID;
};
// General thread information
GLFWGLOBAL struct {
// Critical section lock
pthread_mutex_t CriticalSection;
// Next thread ID to use (increments for every created thread)
GLFWthread NextID;
// First thread in linked list (always the main thread)
_GLFWthread First;
} _glfwThrd;
//========================================================================
// Macros for encapsulating critical code sections (i.e. making parts
// of GLFW thread safe)
//========================================================================
// Define so we can use the same thread code as X11
#define _glfw_numprocessors(n) { \
int mib[2], ncpu; \
size_t len = 1; \
mib[0] = CTL_HW; \
mib[1] = HW_NCPU; \
n = 1; \
if( sysctl( mib, 2, &ncpu, &len, NULL, 0 ) != -1 ) \
{ \
if( len > 0 ) \
{ \
n = ncpu; \
} \
} \
}
// Thread list management
#define ENTER_THREAD_CRITICAL_SECTION \
pthread_mutex_lock( &_glfwThrd.CriticalSection );
#define LEAVE_THREAD_CRITICAL_SECTION \
pthread_mutex_unlock( &_glfwThrd.CriticalSection );
//========================================================================
// Prototypes for platform specific internal functions
//========================================================================
// Time
void _glfwInitTimer( void );
// Joystick
void _glfwInitJoysticks( void );
void _glfwTerminateJoysticks( void );
#endif // _platform_h_
+306
View File
@@ -0,0 +1,306 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Any
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
//************************************************************************
//**** GLFW internal functions ****
//************************************************************************
//========================================================================
// Enable (show) mouse cursor
//========================================================================
static void enableMouseCursor( void )
{
int centerPosX, centerPosY;
if( !_glfwWin.opened || !_glfwWin.mouseLock )
{
return;
}
// Show mouse cursor
_glfwPlatformShowMouseCursor();
centerPosX = _glfwWin.width / 2;
centerPosY = _glfwWin.height / 2;
if( centerPosX != _glfwInput.MousePosX || centerPosY != _glfwInput.MousePosY )
{
_glfwPlatformSetMouseCursorPos( centerPosX, centerPosY );
_glfwInput.MousePosX = centerPosX;
_glfwInput.MousePosY = centerPosY;
if( _glfwWin.mousePosCallback )
{
_glfwWin.mousePosCallback( _glfwInput.MousePosX,
_glfwInput.MousePosY );
}
}
// From now on the mouse is unlocked
_glfwWin.mouseLock = GL_FALSE;
}
//========================================================================
// Disable (hide) mouse cursor
//========================================================================
static void disableMouseCursor( void )
{
if( !_glfwWin.opened || _glfwWin.mouseLock )
{
return;
}
// Hide mouse cursor
_glfwPlatformHideMouseCursor();
// From now on the mouse is locked
_glfwWin.mouseLock = GL_TRUE;
}
//========================================================================
// Enable sticky keys
//========================================================================
static void enableStickyKeys( void )
{
_glfwInput.StickyKeys = 1;
}
//========================================================================
// Disable sticky keys
//========================================================================
static void disableStickyKeys( void )
{
int i;
_glfwInput.StickyKeys = 0;
// Release all sticky keys
for( i = 0; i <= GLFW_KEY_LAST; i++ )
{
if( _glfwInput.Key[ i ] == 2 )
{
_glfwInput.Key[ i ] = 0;
}
}
}
//========================================================================
// Enable sticky mouse buttons
//========================================================================
static void enableStickyMouseButtons( void )
{
_glfwInput.StickyMouseButtons = 1;
}
//========================================================================
// Disable sticky mouse buttons
//========================================================================
static void disableStickyMouseButtons( void )
{
int i;
_glfwInput.StickyMouseButtons = 0;
// Release all sticky mouse buttons
for( i = 0; i <= GLFW_MOUSE_BUTTON_LAST; i++ )
{
if( _glfwInput.MouseButton[ i ] == 2 )
{
_glfwInput.MouseButton[ i ] = 0;
}
}
}
//========================================================================
// Enable system keys
//========================================================================
static void enableSystemKeys( void )
{
if( !_glfwWin.sysKeysDisabled )
{
return;
}
_glfwPlatformEnableSystemKeys();
// Indicate that system keys are no longer disabled
_glfwWin.sysKeysDisabled = GL_FALSE;
}
//========================================================================
// Disable system keys
//========================================================================
static void disableSystemKeys( void )
{
if( _glfwWin.sysKeysDisabled )
{
return;
}
_glfwPlatformDisableSystemKeys();
// Indicate that system keys are now disabled
_glfwWin.sysKeysDisabled = GL_TRUE;
}
//========================================================================
// Enable key repeat
//========================================================================
static void enableKeyRepeat( void )
{
_glfwInput.KeyRepeat = 1;
}
//========================================================================
// Disable key repeat
//========================================================================
static void disableKeyRepeat( void )
{
_glfwInput.KeyRepeat = 0;
}
//========================================================================
// Enable automatic event polling
//========================================================================
static void enableAutoPollEvents( void )
{
_glfwWin.autoPollEvents = 1;
}
//========================================================================
// Disable automatic event polling
//========================================================================
static void disableAutoPollEvents( void )
{
_glfwWin.autoPollEvents = 0;
}
//************************************************************************
//**** GLFW user functions ****
//************************************************************************
//========================================================================
// Enable certain GLFW/window/system functions.
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwEnable( int token )
{
// Is GLFW initialized?
if( !_glfwInitialized )
{
return;
}
switch( token )
{
case GLFW_MOUSE_CURSOR:
enableMouseCursor();
break;
case GLFW_STICKY_KEYS:
enableStickyKeys();
break;
case GLFW_STICKY_MOUSE_BUTTONS:
enableStickyMouseButtons();
break;
case GLFW_SYSTEM_KEYS:
enableSystemKeys();
break;
case GLFW_KEY_REPEAT:
enableKeyRepeat();
break;
case GLFW_AUTO_POLL_EVENTS:
enableAutoPollEvents();
break;
default:
break;
}
}
//========================================================================
// Disable certain GLFW/window/system functions.
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwDisable( int token )
{
// Is GLFW initialized?
if( !_glfwInitialized )
{
return;
}
switch( token )
{
case GLFW_MOUSE_CURSOR:
disableMouseCursor();
break;
case GLFW_STICKY_KEYS:
disableStickyKeys();
break;
case GLFW_STICKY_MOUSE_BUTTONS:
disableStickyMouseButtons();
break;
case GLFW_SYSTEM_KEYS:
disableSystemKeys();
break;
case GLFW_KEY_REPEAT:
disableKeyRepeat();
break;
case GLFW_AUTO_POLL_EVENTS:
disableAutoPollEvents();
break;
default:
break;
}
}
+94
View File
@@ -0,0 +1,94 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Any
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
//************************************************************************
//**** GLFW user functions ****
//************************************************************************
//========================================================================
// Get a list of available video modes
//========================================================================
GLFWAPI int GLFWAPIENTRY glfwGetVideoModes( GLFWvidmode *list, int maxcount )
{
int count, i, swap, res1, res2, depth1, depth2;
GLFWvidmode vm;
if( !_glfwInitialized || maxcount <= 0 || list == (GLFWvidmode*) 0 )
{
return 0;
}
// Get list of video modes
count = _glfwPlatformGetVideoModes( list, maxcount );
// Sort list (bubble sort)
do
{
swap = 0;
for( i = 0; i < count-1; ++ i )
{
res1 = list[i].Width*list[i].Height;
depth1 = list[i].RedBits+list[i].GreenBits+list[i].BlueBits;
res2 = list[i+1].Width*list[i+1].Height;
depth2 = list[i+1].RedBits+list[i+1].GreenBits+
list[i+1].BlueBits;
if( (depth2<depth1) || ((depth2==depth1) && (res2<res1)) )
{
vm = list[i];
list[i] = list[i+1];
list[i+1] = vm;
swap = 1;
}
}
}
while( swap );
return count;
}
//========================================================================
// Get the desktop video mode
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwGetDesktopMode( GLFWvidmode *mode )
{
if( !_glfwInitialized || !mode )
{
return;
}
*mode = _glfwLibrary.desktopMode;
}
+284
View File
@@ -0,0 +1,284 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Any
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
//************************************************************************
//**** GLFW internal functions ****
//************************************************************************
#ifndef GL_VERSION_3_0
#define GL_NUM_EXTENSIONS 0x821D
#define GL_CONTEXT_FLAGS 0x821E
#define GL_CONTEXT_FLAG_FORWARD_COMPATIBLE_BIT 0x0001
#endif
#ifndef GL_VERSION_3_2
#define GL_CONTEXT_CORE_PROFILE_BIT 0x00000001
#define GL_CONTEXT_COMPATIBILITY_PROFILE_BIT 0x00000002
#define GL_CONTEXT_PROFILE_MASK 0x9126
#endif
//========================================================================
// Parses the OpenGL version string and extracts the version number
//========================================================================
void _glfwParseGLVersion( int *major, int *minor, int *rev )
{
GLuint _major, _minor = 0, _rev = 0;
const GLubyte *version;
const GLubyte *ptr;
// Get OpenGL version string
version = glGetString( GL_VERSION );
if( !version )
{
return;
}
// Parse string
ptr = version;
for( _major = 0; *ptr >= '0' && *ptr <= '9'; ptr ++ )
{
_major = 10*_major + (*ptr - '0');
}
if( *ptr == '.' )
{
ptr ++;
for( _minor = 0; *ptr >= '0' && *ptr <= '9'; ptr ++ )
{
_minor = 10*_minor + (*ptr - '0');
}
if( *ptr == '.' )
{
ptr ++;
for( _rev = 0; *ptr >= '0' && *ptr <= '9'; ptr ++ )
{
_rev = 10*_rev + (*ptr - '0');
}
}
}
// Return parsed values
*major = _major;
*minor = _minor;
*rev = _rev;
}
//========================================================================
// Check if a string can be found in an OpenGL extension string
//========================================================================
int _glfwStringInExtensionString( const char *string,
const GLubyte *extensions )
{
const GLubyte *start;
GLubyte *where, *terminator;
// It takes a bit of care to be fool-proof about parsing the
// OpenGL extensions string. Don't be fooled by sub-strings,
// etc.
start = extensions;
for(;;)
{
where = (GLubyte *) strstr( (const char *) start, string );
if( !where )
{
return GL_FALSE;
}
terminator = where + strlen( string );
if( where == start || *(where - 1) == ' ' )
{
if( *terminator == ' ' || *terminator == '\0' )
{
break;
}
}
start = terminator;
}
return GL_TRUE;
}
//========================================================================
// Reads back OpenGL context properties from the current context
//========================================================================
void _glfwRefreshContextParams( void )
{
_glfwParseGLVersion( &_glfwWin.glMajor, &_glfwWin.glMinor,
&_glfwWin.glRevision );
_glfwWin.glProfile = 0;
_glfwWin.glForward = GL_FALSE;
// Read back the context profile, if applicable
if( _glfwWin.glMajor >= 3 )
{
GLint flags;
glGetIntegerv( GL_CONTEXT_FLAGS, &flags );
if( flags & GL_CONTEXT_FLAG_FORWARD_COMPATIBLE_BIT )
{
_glfwWin.glForward = GL_TRUE;
}
}
if( _glfwWin.glMajor > 3 ||
( _glfwWin.glMajor == 3 && _glfwWin.glMinor >= 2 ) )
{
GLint mask;
glGetIntegerv( GL_CONTEXT_PROFILE_MASK, &mask );
if( mask & GL_CONTEXT_COMPATIBILITY_PROFILE_BIT )
{
_glfwWin.glProfile = GLFW_OPENGL_COMPAT_PROFILE;
}
else if( mask & GL_CONTEXT_CORE_PROFILE_BIT )
{
_glfwWin.glProfile = GLFW_OPENGL_CORE_PROFILE;
}
}
}
//************************************************************************
//**** GLFW user functions ****
//************************************************************************
//========================================================================
// Check if an OpenGL extension is available at runtime
//========================================================================
GLFWAPI int GLFWAPIENTRY glfwExtensionSupported( const char *extension )
{
const GLubyte *extensions;
GLubyte *where;
// Is GLFW initialized?
if( !_glfwInitialized || !_glfwWin.opened )
{
return GL_FALSE;
}
// Extension names should not have spaces
where = (GLubyte *) strchr( extension, ' ' );
if( where || *extension == '\0' )
{
return GL_FALSE;
}
if( _glfwWin.glMajor < 3 )
{
// Check if extension is in the old style OpenGL extensions string
extensions = glGetString( GL_EXTENSIONS );
if( extensions != NULL )
{
if( _glfwStringInExtensionString( extension, extensions ) )
{
return GL_TRUE;
}
}
}
else
{
// Check if extension is in the modern OpenGL extensions string list
GLint count;
int i;
glGetIntegerv( GL_NUM_EXTENSIONS, &count );
for( i = 0; i < count; i++ )
{
if( strcmp( (const char*) _glfwWin.GetStringi( GL_EXTENSIONS, i ),
extension ) == 0 )
{
return GL_TRUE;
}
}
}
// Additional platform specific extension checking (e.g. WGL)
if( _glfwPlatformExtensionSupported( extension ) )
{
return GL_TRUE;
}
return GL_FALSE;
}
//========================================================================
// Get the function pointer to an OpenGL function. This function can be
// used to get access to extended OpenGL functions.
//========================================================================
GLFWAPI void * GLFWAPIENTRY glfwGetProcAddress( const char *procname )
{
// Is GLFW initialized?
if( !_glfwInitialized || !_glfwWin.opened )
{
return NULL;
}
return _glfwPlatformGetProcAddress( procname );
}
//========================================================================
// Returns the OpenGL version
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwGetGLVersion( int *major, int *minor, int *rev )
{
// Is GLFW initialized?
if( !_glfwInitialized || !_glfwWin.opened )
{
return;
}
if( major != NULL )
{
*major = _glfwWin.glMajor;
}
if( minor != NULL )
{
*minor = _glfwWin.glMinor;
}
if( rev != NULL )
{
*rev = _glfwWin.glRevision;
}
}
+629
View File
@@ -0,0 +1,629 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Any
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
//========================================================================
// Description:
//
// This module acts as an interface for different image file formats (the
// image file format is detected automatically).
//
// By default the loaded image is rescaled (using bilinear interpolation)
// to the next higher 2^N x 2^M resolution, unless it has a valid
// 2^N x 2^M resolution. The interpolation is quite slow, even if the
// routine has been optimized for speed (a 200x200 RGB image is scaled to
// 256x256 in ~30 ms on a P3-500).
//
// Paletted images are converted to RGB/RGBA images.
//
// A convenience function is also included (glfwLoadTexture2D), which
// loads a texture image from a file directly to OpenGL texture memory,
// with an option to generate all mipmap levels. GL_SGIS_generate_mipmap
// is used whenever available, which should give an optimal mipmap
// generation speed (possibly performed in hardware). A software fallback
// method is included when GL_SGIS_generate_mipmap is not supported (it
// generates all mipmaps of a 256x256 RGB texture in ~3 ms on a P3-500).
//
//========================================================================
#include "internal.h"
// We want to support automatic mipmap generation
#ifndef GL_SGIS_generate_mipmap
#define GL_GENERATE_MIPMAP_SGIS 0x8191
#define GL_GENERATE_MIPMAP_HINT_SGIS 0x8192
#define GL_SGIS_generate_mipmap 1
#endif // GL_SGIS_generate_mipmap
//************************************************************************
//**** GLFW internal functions ****
//************************************************************************
//========================================================================
// Upsample image, from size w1 x h1 to w2 x h2
//========================================================================
static void UpsampleImage( unsigned char *src, unsigned char *dst,
int w1, int h1, int w2, int h2, int bpp )
{
int m, n, k, x, y, col8;
float dx, dy, xstep, ystep, col, col1, col2;
unsigned char *src1, *src2, *src3, *src4;
// Calculate scaling factor
xstep = (float)(w1-1) / (float)(w2-1);
ystep = (float)(h1-1) / (float)(h2-1);
// Copy source data to destination data with bilinear interpolation
// Note: The rather strange look of this routine is a direct result of
// my attempts at optimizing it. Improvements are welcome!
dy = 0.0f;
y = 0;
for( n = 0; n < h2; n ++ )
{
dx = 0.0f;
src1 = &src[ y*w1*bpp ];
src3 = y < (h1-1) ? src1 + w1*bpp : src1;
src2 = src1 + bpp;
src4 = src3 + bpp;
x = 0;
for( m = 0; m < w2; m ++ )
{
for( k = 0; k < bpp; k ++ )
{
col1 = *src1 ++;
col2 = *src2 ++;
col = col1 + (col2 - col1) * dx;
col1 = *src3 ++;
col2 = *src4 ++;
col2 = col1 + (col2 - col1) * dx;
col += (col2 - col) * dy;
col8 = (int) (col + 0.5);
if( col8 >= 256 ) col8 = 255;
*dst++ = (unsigned char) col8;
}
dx += xstep;
if( dx >= 1.0f )
{
x ++;
dx -= 1.0f;
if( x >= (w1-1) )
{
src2 = src1;
src4 = src3;
}
}
else
{
src1 -= bpp;
src2 -= bpp;
src3 -= bpp;
src4 -= bpp;
}
}
dy += ystep;
if( dy >= 1.0f )
{
y ++;
dy -= 1.0f;
}
}
}
//========================================================================
// Build the next mip-map level
//========================================================================
static int HalveImage( GLubyte *src, int *width, int *height,
int components )
{
int halfwidth, halfheight, m, n, k, idx1, idx2;
GLubyte *dst;
// Last level?
if( *width <= 1 && *height <= 1 )
{
return GL_FALSE;
}
// Calculate new width and height (handle 1D case)
halfwidth = *width > 1 ? *width / 2 : 1;
halfheight = *height > 1 ? *height / 2 : 1;
// Downsample image with a simple box-filter
dst = src;
if( *width == 1 || *height == 1 )
{
// 1D case
for( m = 0; m < halfwidth+halfheight-1; m ++ )
{
for( k = 0; k < components; k ++ )
{
*dst ++ = (GLubyte) (((int)*src +
(int)src[components] + 1) >> 1);
src ++;
}
src += components;
}
}
else
{
// 2D case
idx1 = *width*components;
idx2 = (*width+1)*components;
for( m = 0; m < halfheight; m ++ )
{
for( n = 0; n < halfwidth; n ++ )
{
for( k = 0; k < components; k ++ )
{
*dst ++ = (GLubyte) (((int)*src +
(int)src[components] +
(int)src[idx1] +
(int)src[idx2] + 2) >> 2);
src ++;
}
src += components;
}
src += components * (*width);
}
}
// Return new width and height
*width = halfwidth;
*height = halfheight;
return GL_TRUE;
}
//========================================================================
// Rescales an image into power-of-two dimensions
//========================================================================
static int RescaleImage( GLFWimage* image )
{
int width, height, log2, newsize;
unsigned char *data;
// Calculate next larger 2^N width
for( log2 = 0, width = image->Width; width > 1; width >>= 1, log2 ++ )
;
width = (int) 1 << log2;
if( width < image->Width )
{
width <<= 1;
}
// Calculate next larger 2^M height
for( log2 = 0, height = image->Height; height > 1; height >>= 1, log2 ++ )
;
height = (int) 1 << log2;
if( height < image->Height )
{
height <<= 1;
}
// Do we really need to rescale?
if( width != image->Width || height != image->Height )
{
// Allocate memory for new (upsampled) image data
newsize = width * height * image->BytesPerPixel;
data = (unsigned char *) malloc( newsize );
if( data == NULL )
{
free( image->Data );
return GL_FALSE;
}
// Copy old image data to new image data with interpolation
UpsampleImage( image->Data, data, image->Width, image->Height,
width, height, image->BytesPerPixel );
// Free memory for old image data (not needed anymore)
free( image->Data );
// Set pointer to new image data, and set new image dimensions
image->Data = data;
image->Width = width;
image->Height = height;
}
return GL_TRUE;
}
//************************************************************************
//**** GLFW user functions ****
//************************************************************************
//========================================================================
// Read an image from a named file
//========================================================================
GLFWAPI int GLFWAPIENTRY glfwReadImage( const char *name, GLFWimage *img,
int flags )
{
_GLFWstream stream;
// Is GLFW initialized?
if( !_glfwInitialized )
{
return GL_FALSE;
}
// Start with an empty image descriptor
img->Width = 0;
img->Height = 0;
img->BytesPerPixel = 0;
img->Data = NULL;
// Open file
if( !_glfwOpenFileStream( &stream, name, "rb" ) )
{
return GL_FALSE;
}
// We only support TGA files at the moment
if( !_glfwReadTGA( &stream, img, flags ) )
{
_glfwCloseStream( &stream );
return GL_FALSE;
}
// Close stream
_glfwCloseStream( &stream );
// Should we rescale the image to closest 2^N x 2^M resolution?
if( !(flags & GLFW_NO_RESCALE_BIT) )
{
if( !RescaleImage( img ) )
{
return GL_FALSE;
}
}
// Interpret BytesPerPixel as an OpenGL format
switch( img->BytesPerPixel )
{
default:
case 1:
if( flags & GLFW_ALPHA_MAP_BIT )
{
img->Format = GL_ALPHA;
}
else
{
img->Format = GL_LUMINANCE;
}
break;
case 3:
img->Format = GL_RGB;
break;
case 4:
img->Format = GL_RGBA;
break;
}
return GL_TRUE;
}
//========================================================================
// Read an image file from a memory buffer
//========================================================================
GLFWAPI int GLFWAPIENTRY glfwReadMemoryImage( const void *data, long size, GLFWimage *img, int flags )
{
_GLFWstream stream;
// Is GLFW initialized?
if( !_glfwInitialized )
{
return GL_FALSE;
}
// Start with an empty image descriptor
img->Width = 0;
img->Height = 0;
img->BytesPerPixel = 0;
img->Data = NULL;
// Open buffer
if( !_glfwOpenBufferStream( &stream, (void*) data, size ) )
{
return GL_FALSE;
}
// We only support TGA files at the moment
if( !_glfwReadTGA( &stream, img, flags ) )
{
_glfwCloseStream( &stream );
return GL_FALSE;
}
// Close stream
_glfwCloseStream( &stream );
// Should we rescale the image to closest 2^N x 2^M resolution?
if( !(flags & GLFW_NO_RESCALE_BIT) )
{
if( !RescaleImage( img ) )
{
return GL_FALSE;
}
}
// Interpret BytesPerPixel as an OpenGL format
switch( img->BytesPerPixel )
{
default:
case 1:
if( flags & GLFW_ALPHA_MAP_BIT )
{
img->Format = GL_ALPHA;
}
else
{
img->Format = GL_LUMINANCE;
}
break;
case 3:
img->Format = GL_RGB;
break;
case 4:
img->Format = GL_RGBA;
break;
}
return GL_TRUE;
}
//========================================================================
// Free allocated memory for an image
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwFreeImage( GLFWimage *img )
{
// Is GLFW initialized?
if( !_glfwInitialized )
{
return;
}
// Free memory
if( img->Data != NULL )
{
free( img->Data );
img->Data = NULL;
}
// Clear all fields
img->Width = 0;
img->Height = 0;
img->Format = 0;
img->BytesPerPixel = 0;
}
//========================================================================
// Read an image from a file, and upload it to texture memory
//========================================================================
GLFWAPI int GLFWAPIENTRY glfwLoadTexture2D( const char *name, int flags )
{
GLFWimage img;
// Is GLFW initialized?
if( !_glfwInitialized || !_glfwWin.opened )
{
return GL_FALSE;
}
// Force rescaling if necessary
if( !_glfwWin.has_GL_ARB_texture_non_power_of_two )
{
flags &= (~GLFW_NO_RESCALE_BIT);
}
// Read image from file
if( !glfwReadImage( name, &img, flags ) )
{
return GL_FALSE;
}
if( !glfwLoadTextureImage2D( &img, flags ) )
{
return GL_FALSE;
}
// Data buffer is not needed anymore
glfwFreeImage( &img );
return GL_TRUE;
}
//========================================================================
// Read an image from a buffer, and upload it to texture memory
//========================================================================
GLFWAPI int GLFWAPIENTRY glfwLoadMemoryTexture2D( const void *data, long size, int flags )
{
GLFWimage img;
// Is GLFW initialized?
if( !_glfwInitialized || !_glfwWin.opened )
{
return GL_FALSE;
}
// Force rescaling if necessary
if( !_glfwWin.has_GL_ARB_texture_non_power_of_two )
{
flags &= (~GLFW_NO_RESCALE_BIT);
}
// Read image from file
if( !glfwReadMemoryImage( data, size, &img, flags ) )
{
return GL_FALSE;
}
if( !glfwLoadTextureImage2D( &img, flags ) )
{
return GL_FALSE;
}
// Data buffer is not needed anymore
glfwFreeImage( &img );
return GL_TRUE;
}
//========================================================================
// Upload an image object to texture memory
//========================================================================
GLFWAPI int GLFWAPIENTRY glfwLoadTextureImage2D( GLFWimage *img, int flags )
{
GLint UnpackAlignment, GenMipMap = 0;
int level, format, AutoGen, newsize, n;
unsigned char *data, *dataptr;
// Is GLFW initialized?
if( !_glfwInitialized || !_glfwWin.opened )
{
return GL_FALSE;
}
// TODO: Use GL_MAX_TEXTURE_SIZE or GL_PROXY_TEXTURE_2D to determine
// whether the image size is valid.
// NOTE: May require box filter downsampling routine.
// Do we need to convert the alpha map to RGBA format (OpenGL 1.0)?
if( (_glfwWin.glMajor == 1) && (_glfwWin.glMinor == 0) &&
(img->Format == GL_ALPHA) )
{
// We go to RGBA representation instead
img->BytesPerPixel = 4;
// Allocate memory for new RGBA image data
newsize = img->Width * img->Height * img->BytesPerPixel;
data = (unsigned char *) malloc( newsize );
if( data == NULL )
{
free( img->Data );
return GL_FALSE;
}
// Convert Alpha map to RGBA
dataptr = data;
for( n = 0; n < (img->Width*img->Height); ++ n )
{
*dataptr ++ = 255;
*dataptr ++ = 255;
*dataptr ++ = 255;
*dataptr ++ = img->Data[n];
}
// Free memory for old image data (not needed anymore)
free( img->Data );
// Set pointer to new image data
img->Data = data;
}
// Set unpack alignment to one byte
glGetIntegerv( GL_UNPACK_ALIGNMENT, &UnpackAlignment );
glPixelStorei( GL_UNPACK_ALIGNMENT, 1 );
// Should we use automatic mipmap generation?
AutoGen = ( flags & GLFW_BUILD_MIPMAPS_BIT ) &&
_glfwWin.has_GL_SGIS_generate_mipmap;
// Enable automatic mipmap generation
if( AutoGen )
{
glGetTexParameteriv( GL_TEXTURE_2D, GL_GENERATE_MIPMAP_SGIS,
&GenMipMap );
glTexParameteri( GL_TEXTURE_2D, GL_GENERATE_MIPMAP_SGIS,
GL_TRUE );
}
// Format specification is different for OpenGL 1.0
if( _glfwWin.glMajor == 1 && _glfwWin.glMinor == 0 )
{
format = img->BytesPerPixel;
}
else
{
format = img->Format;
}
// Upload to texture memeory
level = 0;
do
{
// Upload this mipmap level
glTexImage2D( GL_TEXTURE_2D, level, format,
img->Width, img->Height, 0, format,
GL_UNSIGNED_BYTE, (void*) img->Data );
// Build next mipmap level manually, if required
if( ( flags & GLFW_BUILD_MIPMAPS_BIT ) && !AutoGen )
{
level = HalveImage( img->Data, &img->Width,
&img->Height, img->BytesPerPixel ) ?
level + 1 : 0;
}
}
while( level != 0 );
// Restore old automatic mipmap generation state
if( AutoGen )
{
glTexParameteri( GL_TEXTURE_2D, GL_GENERATE_MIPMAP_SGIS,
GenMipMap );
}
// Restore old unpack alignment
glPixelStorei( GL_UNPACK_ALIGNMENT, UnpackAlignment );
return GL_TRUE;
}
+110
View File
@@ -0,0 +1,110 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Any
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#define _init_c_
#include "internal.h"
//************************************************************************
//**** GLFW user functions ****
//************************************************************************
//========================================================================
// Initialize various GLFW state
//========================================================================
GLFWAPI int GLFWAPIENTRY glfwInit( void )
{
// Is GLFW already initialized?
if( _glfwInitialized )
{
return GL_TRUE;
}
memset( &_glfwLibrary, 0, sizeof( _glfwLibrary ) );
memset( &_glfwWin, 0, sizeof( _glfwWin ) );
// Window is not yet opened
_glfwWin.opened = GL_FALSE;
// Default enable/disable settings
_glfwWin.sysKeysDisabled = GL_FALSE;
// Clear window hints
_glfwClearWindowHints();
// Platform specific initialization
if( !_glfwPlatformInit() )
{
return GL_FALSE;
}
// Form now on, GLFW state is valid
_glfwInitialized = GL_TRUE;
return GL_TRUE;
}
//========================================================================
// Close window and kill all threads.
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwTerminate( void )
{
// Is GLFW initialized?
if( !_glfwInitialized )
{
return;
}
// Platform specific termination
if( !_glfwPlatformTerminate() )
{
return;
}
// GLFW is no longer initialized
_glfwInitialized = GL_FALSE;
}
//========================================================================
// Get GLFW version
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwGetVersion( int *major, int *minor, int *rev )
{
if( major != NULL ) *major = GLFW_VERSION_MAJOR;
if( minor != NULL ) *minor = GLFW_VERSION_MINOR;
if( rev != NULL ) *rev = GLFW_VERSION_REVISION;
}
+269
View File
@@ -0,0 +1,269 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Any
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
//========================================================================
// Return key state
//========================================================================
GLFWAPI int GLFWAPIENTRY glfwGetKey( int key )
{
if( !_glfwInitialized || !_glfwWin.opened )
{
return GLFW_RELEASE;
}
// Is it a valid key?
if( key < 0 || key > GLFW_KEY_LAST )
{
return GLFW_RELEASE;
}
if( _glfwInput.Key[ key ] == GLFW_STICK )
{
// Sticky mode: release key now
_glfwInput.Key[ key ] = GLFW_RELEASE;
return GLFW_PRESS;
}
return (int) _glfwInput.Key[ key ];
}
//========================================================================
// Return mouse button state
//========================================================================
GLFWAPI int GLFWAPIENTRY glfwGetMouseButton( int button )
{
if( !_glfwInitialized || !_glfwWin.opened )
{
return GLFW_RELEASE;
}
// Is it a valid mouse button?
if( button < 0 || button > GLFW_MOUSE_BUTTON_LAST )
{
return GLFW_RELEASE;
}
if( _glfwInput.MouseButton[ button ] == GLFW_STICK )
{
// Sticky mode: release mouse button now
_glfwInput.MouseButton[ button ] = GLFW_RELEASE;
return GLFW_PRESS;
}
return (int) _glfwInput.MouseButton[ button ];
}
//========================================================================
// Return mouse cursor position
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwGetMousePos( int *xpos, int *ypos )
{
if( !_glfwInitialized || !_glfwWin.opened )
{
return;
}
// Return mouse position
if( xpos != NULL )
{
*xpos = _glfwInput.MousePosX;
}
if( ypos != NULL )
{
*ypos = _glfwInput.MousePosY;
}
}
//========================================================================
// Sets the mouse cursor position
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwSetMousePos( int xpos, int ypos )
{
if( !_glfwInitialized || !_glfwWin.opened )
{
return;
}
// Don't do anything if the mouse position did not change
if( xpos == _glfwInput.MousePosX && ypos == _glfwInput.MousePosY )
{
return;
}
// Set GLFW mouse position
_glfwInput.MousePosX = xpos;
_glfwInput.MousePosY = ypos;
// If we have a locked mouse, do not change cursor position
if( _glfwWin.mouseLock )
{
return;
}
// Update physical cursor position
_glfwPlatformSetMouseCursorPos( xpos, ypos );
}
//========================================================================
// Return mouse wheel position
//========================================================================
GLFWAPI int GLFWAPIENTRY glfwGetMouseWheel( void )
{
if( !_glfwInitialized || !_glfwWin.opened )
{
return 0;
}
// Return mouse wheel position
return _glfwInput.WheelPos;
}
//========================================================================
// Set mouse wheel position
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwSetMouseWheel( int pos )
{
if( !_glfwInitialized || !_glfwWin.opened )
{
return;
}
// Set mouse wheel position
_glfwInput.WheelPos = pos;
}
//========================================================================
// Set callback function for keyboard input
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwSetKeyCallback( GLFWkeyfun cbfun )
{
if( !_glfwInitialized || !_glfwWin.opened )
{
return;
}
// Set callback function
_glfwWin.keyCallback = cbfun;
}
//========================================================================
// Set callback function for character input
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwSetCharCallback( GLFWcharfun cbfun )
{
if( !_glfwInitialized || !_glfwWin.opened )
{
return;
}
// Set callback function
_glfwWin.charCallback = cbfun;
}
//========================================================================
// Set callback function for mouse clicks
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwSetMouseButtonCallback( GLFWmousebuttonfun cbfun )
{
if( !_glfwInitialized || !_glfwWin.opened )
{
return;
}
// Set callback function
_glfwWin.mouseButtonCallback = cbfun;
}
//========================================================================
// Set callback function for mouse moves
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwSetMousePosCallback( GLFWmouseposfun cbfun )
{
if( !_glfwInitialized || !_glfwWin.opened )
{
return;
}
// Set callback function
_glfwWin.mousePosCallback = cbfun;
// Call the callback function to let the application know the current
// mouse position
if( cbfun )
{
cbfun( _glfwInput.MousePosX, _glfwInput.MousePosY );
}
}
//========================================================================
// Set callback function for mouse wheel
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwSetMouseWheelCallback( GLFWmousewheelfun cbfun )
{
if( !_glfwInitialized || !_glfwWin.opened )
{
return;
}
// Set callback function
_glfwWin.mouseWheelCallback = cbfun;
// Call the callback function to let the application know the current
// mouse wheel position
if( cbfun )
{
cbfun( _glfwInput.WheelPos );
}
}
+271
View File
@@ -0,0 +1,271 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Any
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#ifndef _internal_h_
#define _internal_h_
//========================================================================
// GLFWGLOBAL is a macro that places all global variables in the init.c
// module (all other modules reference global variables as 'extern')
//========================================================================
#if defined( _init_c_ )
#define GLFWGLOBAL
#else
#define GLFWGLOBAL extern
#endif
//========================================================================
// Input handling definitions
//========================================================================
// Internal key and button state/action definitions
#define GLFW_STICK 2
//========================================================================
// System independent include files
//========================================================================
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
//------------------------------------------------------------------------
// Window opening hints (set by glfwOpenWindowHint)
// A bucket of semi-random stuff bunched together for historical reasons
// This is used only by the platform independent code and only to store
// parameters passed to us by glfwOpenWindowHint
//------------------------------------------------------------------------
typedef struct {
int refreshRate;
int accumRedBits;
int accumGreenBits;
int accumBlueBits;
int accumAlphaBits;
int auxBuffers;
int stereo;
int windowNoResize;
int samples;
int glMajor;
int glMinor;
int glForward;
int glDebug;
int glProfile;
} _GLFWhints;
//------------------------------------------------------------------------
// Platform specific definitions goes in platform.h (which also includes
// glfw.h)
//------------------------------------------------------------------------
#if __APPLE__
#include "cocoa/platform.h"
#elif WIN32
#include "win32/platform.h"
#else
#include "x11/platform.h"
#endif
//------------------------------------------------------------------------
// Parameters relating to the creation of the context and window but not
// directly related to the properties of the framebuffer
// This is used to pass window and context creation parameters from the
// platform independent code to the platform specific code
//------------------------------------------------------------------------
typedef struct {
int mode;
int refreshRate;
int windowNoResize;
int glMajor;
int glMinor;
int glForward;
int glDebug;
int glProfile;
} _GLFWwndconfig;
//------------------------------------------------------------------------
// Framebuffer configuration descriptor, i.e. buffers and their sizes
// Also a platform specific ID used to map back to the actual backend APIs
// This is used to pass framebuffer parameters from the platform independent
// code to the platform specific code, and also to enumerate and select
// available framebuffer configurations
//------------------------------------------------------------------------
typedef struct {
int redBits;
int greenBits;
int blueBits;
int alphaBits;
int depthBits;
int stencilBits;
int accumRedBits;
int accumGreenBits;
int accumBlueBits;
int accumAlphaBits;
int auxBuffers;
int stereo;
int samples;
GLFWintptr platformID;
} _GLFWfbconfig;
//========================================================================
// System independent global variables (GLFW internals)
//========================================================================
// Flag indicating if GLFW has been initialized
#if defined( _init_c_ )
int _glfwInitialized = 0;
#else
GLFWGLOBAL int _glfwInitialized;
#endif
//------------------------------------------------------------------------
// Abstract data stream (for image I/O)
//------------------------------------------------------------------------
typedef struct {
FILE* file;
void* data;
long position;
long size;
} _GLFWstream;
//========================================================================
// Prototypes for platform specific implementation functions
//========================================================================
// Init/terminate
int _glfwPlatformInit( void );
int _glfwPlatformTerminate( void );
// Enable/Disable
void _glfwPlatformEnableSystemKeys( void );
void _glfwPlatformDisableSystemKeys( void );
// Fullscreen
int _glfwPlatformGetVideoModes( GLFWvidmode *list, int maxcount );
void _glfwPlatformGetDesktopMode( GLFWvidmode *mode );
// OpenGL extensions
int _glfwPlatformExtensionSupported( const char *extension );
void * _glfwPlatformGetProcAddress( const char *procname );
// Joystick
int _glfwPlatformGetJoystickParam( int joy, int param );
int _glfwPlatformGetJoystickPos( int joy, float *pos, int numaxes );
int _glfwPlatformGetJoystickButtons( int joy, unsigned char *buttons, int numbuttons );
// Threads
GLFWthread _glfwPlatformCreateThread( GLFWthreadfun fun, void *arg );
void _glfwPlatformDestroyThread( GLFWthread ID );
int _glfwPlatformWaitThread( GLFWthread ID, int waitmode );
GLFWthread _glfwPlatformGetThreadID( void );
GLFWmutex _glfwPlatformCreateMutex( void );
void _glfwPlatformDestroyMutex( GLFWmutex mutex );
void _glfwPlatformLockMutex( GLFWmutex mutex );
void _glfwPlatformUnlockMutex( GLFWmutex mutex );
GLFWcond _glfwPlatformCreateCond( void );
void _glfwPlatformDestroyCond( GLFWcond cond );
void _glfwPlatformWaitCond( GLFWcond cond, GLFWmutex mutex, double timeout );
void _glfwPlatformSignalCond( GLFWcond cond );
void _glfwPlatformBroadcastCond( GLFWcond cond );
int _glfwPlatformGetNumberOfProcessors( void );
// Time
double _glfwPlatformGetTime( void );
void _glfwPlatformSetTime( double time );
void _glfwPlatformSleep( double time );
// Window management
int _glfwPlatformOpenWindow( int width, int height, const _GLFWwndconfig *wndconfig, const _GLFWfbconfig *fbconfig );
void _glfwPlatformCloseWindow( void );
void _glfwPlatformSetWindowTitle( const char *title );
void _glfwPlatformSetWindowSize( int width, int height );
void _glfwPlatformSetWindowPos( int x, int y );
void _glfwPlatformIconifyWindow( void );
void _glfwPlatformRestoreWindow( void );
void _glfwPlatformSwapBuffers( void );
void _glfwPlatformSwapInterval( int interval );
void _glfwPlatformRefreshWindowParams( void );
void _glfwPlatformPollEvents( void );
void _glfwPlatformWaitEvents( void );
void _glfwPlatformHideMouseCursor( void );
void _glfwPlatformShowMouseCursor( void );
void _glfwPlatformSetMouseCursorPos( int x, int y );
//========================================================================
// Prototypes for platform independent internal functions
//========================================================================
// Window management (window.c)
void _glfwClearWindowHints( void );
// Input handling (window.c)
void _glfwClearInput( void );
void _glfwInputDeactivation( void );
void _glfwInputKey( int key, int action );
void _glfwInputChar( int character, int action );
void _glfwInputMouseClick( int button, int action );
// Threads (thread.c)
_GLFWthread * _glfwGetThreadPointer( int ID );
void _glfwAppendThread( _GLFWthread * t );
void _glfwRemoveThread( _GLFWthread * t );
// OpenGL extensions (glext.c)
void _glfwParseGLVersion( int *major, int *minor, int *rev );
int _glfwStringInExtensionString( const char *string, const GLubyte *extensions );
void _glfwRefreshContextParams( void );
// Abstracted data streams (stream.c)
int _glfwOpenFileStream( _GLFWstream *stream, const char *name, const char *mode );
int _glfwOpenBufferStream( _GLFWstream *stream, void *data, long size );
long _glfwReadStream( _GLFWstream *stream, void *data, long size );
long _glfwTellStream( _GLFWstream *stream );
int _glfwSeekStream( _GLFWstream *stream, long offset, int whence );
void _glfwCloseStream( _GLFWstream *stream );
// Targa image I/O (tga.c)
int _glfwReadTGA( _GLFWstream *s, GLFWimage *img, int flags );
// Framebuffer configs
const _GLFWfbconfig *_glfwChooseFBConfig( const _GLFWfbconfig *desired,
const _GLFWfbconfig *alternatives,
unsigned int count );
#endif // _internal_h_
+99
View File
@@ -0,0 +1,99 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Any
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
//************************************************************************
//**** GLFW user functions ****
//************************************************************************
//========================================================================
// Determine joystick capabilities
//========================================================================
GLFWAPI int GLFWAPIENTRY glfwGetJoystickParam( int joy, int param )
{
if( !_glfwInitialized )
{
return 0;
}
return _glfwPlatformGetJoystickParam( joy, param );
}
//========================================================================
// Get joystick axis positions
//========================================================================
GLFWAPI int GLFWAPIENTRY glfwGetJoystickPos( int joy, float *pos, int numaxes )
{
int i;
if( !_glfwInitialized )
{
return 0;
}
// Clear positions
for( i = 0; i < numaxes; i++ )
{
pos[ i ] = 0.0f;
}
return _glfwPlatformGetJoystickPos( joy, pos, numaxes );
}
//========================================================================
// Get joystick button states
//========================================================================
GLFWAPI int GLFWAPIENTRY glfwGetJoystickButtons( int joy,
unsigned char *buttons,
int numbuttons )
{
int i;
if( !_glfwInitialized )
{
return 0;
}
// Clear button states
for( i = 0; i < numbuttons; i++ )
{
buttons[ i ] = GLFW_RELEASE;
}
return _glfwPlatformGetJoystickButtons( joy, buttons, numbuttons );
}
+194
View File
@@ -0,0 +1,194 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Any
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
//========================================================================
// Opens a GLFW stream with a file
//========================================================================
int _glfwOpenFileStream( _GLFWstream *stream, const char* name, const char* mode )
{
memset( stream, 0, sizeof(_GLFWstream) );
stream->file = fopen( name, mode );
if( stream->file == NULL )
{
return GL_FALSE;
}
return GL_TRUE;
}
//========================================================================
// Opens a GLFW stream with a memory block
//========================================================================
int _glfwOpenBufferStream( _GLFWstream *stream, void *data, long size )
{
memset( stream, 0, sizeof(_GLFWstream) );
stream->data = data;
stream->size = size;
return GL_TRUE;
}
//========================================================================
// Reads data from a GLFW stream
//========================================================================
long _glfwReadStream( _GLFWstream *stream, void *data, long size )
{
if( stream->file != NULL )
{
return (long) fread( data, 1, size, stream->file );
}
if( stream->data != NULL )
{
// Check for EOF
if( stream->position == stream->size )
{
return 0;
}
// Clamp read size to available data
if( stream->position + size > stream->size )
{
size = stream->size - stream->position;
}
// Perform data read
memcpy( data, (unsigned char*) stream->data + stream->position, size );
stream->position += size;
return size;
}
return 0;
}
//========================================================================
// Returns the current position of a GLFW stream
//========================================================================
long _glfwTellStream( _GLFWstream *stream )
{
if( stream->file != NULL )
{
return ftell( stream->file );
}
if( stream->data != NULL )
{
return stream->position;
}
return 0;
}
//========================================================================
// Sets the current position of a GLFW stream
//========================================================================
int _glfwSeekStream( _GLFWstream *stream, long offset, int whence )
{
long position;
if( stream->file != NULL )
{
if( fseek( stream->file, offset, whence ) != 0 )
{
return GL_FALSE;
}
return GL_TRUE;
}
if( stream->data != NULL )
{
position = offset;
// Handle whence parameter
if( whence == SEEK_CUR )
{
position += stream->position;
}
else if( whence == SEEK_END )
{
position += stream->size;
}
else if( whence != SEEK_SET )
{
return GL_FALSE;
}
// Clamp offset to buffer bounds and apply it
if( position > stream->size )
{
stream->position = stream->size;
}
else if( position < 0 )
{
stream->position = 0;
}
else
{
stream->position = position;
}
return GL_TRUE;
}
return GL_FALSE;
}
//========================================================================
// Closes a GLFW stream
//========================================================================
void _glfwCloseStream( _GLFWstream *stream )
{
if( stream->file != NULL )
{
fclose( stream->file );
}
// Nothing to be done about (user allocated) memory blocks
memset( stream, 0, sizeof(_GLFWstream) );
}
+404
View File
@@ -0,0 +1,404 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Any
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
//========================================================================
// Description:
//
// TGA format image file loader. This module supports version 1 Targa
// images, with these restrictions:
// - Pixel format may only be 8, 24 or 32 bits
// - Colormaps must be no longer than 256 entries
//
//========================================================================
#include "internal.h"
//************************************************************************
//**** GLFW internal functions & declarations ****
//************************************************************************
//========================================================================
// TGA file header information
//========================================================================
typedef struct {
int idlen; // 1 byte
int cmaptype; // 1 byte
int imagetype; // 1 byte
int cmapfirstidx; // 2 bytes
int cmaplen; // 2 bytes
int cmapentrysize; // 1 byte
int xorigin; // 2 bytes
int yorigin; // 2 bytes
int width; // 2 bytes
int height; // 2 bytes
int bitsperpixel; // 1 byte
int imageinfo; // 1 byte
int _alphabits; // (derived from imageinfo)
int _origin; // (derived from imageinfo)
} _tga_header_t;
#define _TGA_CMAPTYPE_NONE 0
#define _TGA_CMAPTYPE_PRESENT 1
#define _TGA_IMAGETYPE_NONE 0
#define _TGA_IMAGETYPE_CMAP 1
#define _TGA_IMAGETYPE_TC 2
#define _TGA_IMAGETYPE_GRAY 3
#define _TGA_IMAGETYPE_CMAP_RLE 9
#define _TGA_IMAGETYPE_TC_RLE 10
#define _TGA_IMAGETYPE_GRAY_RLE 11
#define _TGA_IMAGEINFO_ALPHA_MASK 0x0f
#define _TGA_IMAGEINFO_ALPHA_SHIFT 0
#define _TGA_IMAGEINFO_ORIGIN_MASK 0x30
#define _TGA_IMAGEINFO_ORIGIN_SHIFT 4
#define _TGA_ORIGIN_BL 0
#define _TGA_ORIGIN_BR 1
#define _TGA_ORIGIN_UL 2
#define _TGA_ORIGIN_UR 3
//========================================================================
// Read TGA file header (and check that it is valid)
//========================================================================
static int ReadTGAHeader( _GLFWstream *s, _tga_header_t *h )
{
unsigned char buf[ 18 ];
int pos;
// Read TGA file header from file
pos = _glfwTellStream( s );
_glfwReadStream( s, buf, 18 );
// Interpret header (endian independent parsing)
h->idlen = (int) buf[0];
h->cmaptype = (int) buf[1];
h->imagetype = (int) buf[2];
h->cmapfirstidx = (int) buf[3] | (((int) buf[4]) << 8);
h->cmaplen = (int) buf[5] | (((int) buf[6]) << 8);
h->cmapentrysize = (int) buf[7];
h->xorigin = (int) buf[8] | (((int) buf[9]) << 8);
h->yorigin = (int) buf[10] | (((int) buf[11]) << 8);
h->width = (int) buf[12] | (((int) buf[13]) << 8);
h->height = (int) buf[14] | (((int) buf[15]) << 8);
h->bitsperpixel = (int) buf[16];
h->imageinfo = (int) buf[17];
// Extract alphabits and origin information
h->_alphabits = (int) (h->imageinfo & _TGA_IMAGEINFO_ALPHA_MASK) >>
_TGA_IMAGEINFO_ALPHA_SHIFT;
h->_origin = (int) (h->imageinfo & _TGA_IMAGEINFO_ORIGIN_MASK) >>
_TGA_IMAGEINFO_ORIGIN_SHIFT;
// Validate TGA header (is this a TGA file?)
if( (h->cmaptype == 0 || h->cmaptype == 1) &&
((h->imagetype >= 1 && h->imagetype <= 3) ||
(h->imagetype >= 9 && h->imagetype <= 11)) &&
(h->bitsperpixel == 8 || h->bitsperpixel == 24 ||
h->bitsperpixel == 32) )
{
// Skip the ID field
_glfwSeekStream( s, h->idlen, SEEK_CUR );
// Indicate that the TGA header was valid
return GL_TRUE;
}
else
{
// Restore file position
_glfwSeekStream( s, pos, SEEK_SET );
// Indicate that the TGA header was invalid
return GL_FALSE;
}
}
//========================================================================
// Read Run-Length Encoded data
//========================================================================
static void ReadTGA_RLE( unsigned char *buf, int size, int bpp,
_GLFWstream *s )
{
int repcount, bytes, k, n;
unsigned char pixel[ 4 ];
char c;
// Dummy check
if( bpp > 4 )
{
return;
}
while( size > 0 )
{
// Get repetition count
_glfwReadStream( s, &c, 1 );
repcount = (unsigned int) c;
bytes = ((repcount & 127) + 1) * bpp;
if( size < bytes )
{
bytes = size;
}
// Run-Length packet?
if( repcount & 128 )
{
_glfwReadStream( s, pixel, bpp );
for( n = 0; n < (repcount & 127) + 1; n ++ )
{
for( k = 0; k < bpp; k ++ )
{
*buf ++ = pixel[ k ];
}
}
}
else
{
// It's a Raw packet
_glfwReadStream( s, buf, bytes );
buf += bytes;
}
size -= bytes;
}
}
//========================================================================
// Read a TGA image from a file
//========================================================================
int _glfwReadTGA( _GLFWstream *s, GLFWimage *img, int flags )
{
_tga_header_t h;
unsigned char *cmap, *pix, tmp, *src, *dst;
int cmapsize, pixsize, pixsize2;
int bpp, bpp2, k, m, n, swapx, swapy;
// Read TGA header
if( !ReadTGAHeader( s, &h ) )
{
return 0;
}
// Is there a colormap?
cmapsize = (h.cmaptype == _TGA_CMAPTYPE_PRESENT ? 1 : 0) * h.cmaplen *
((h.cmapentrysize+7) / 8);
if( cmapsize > 0 )
{
// Is it a colormap that we can handle?
if( (h.cmapentrysize != 24 && h.cmapentrysize != 32) ||
h.cmaplen == 0 || h.cmaplen > 256 )
{
return 0;
}
// Allocate memory for colormap
cmap = (unsigned char *) malloc( cmapsize );
if( cmap == NULL )
{
return 0;
}
// Read colormap from file
_glfwReadStream( s, cmap, cmapsize );
}
else
{
cmap = NULL;
}
// Size of pixel data
pixsize = h.width * h.height * ((h.bitsperpixel + 7) / 8);
// Bytes per pixel (pixel data - unexpanded)
bpp = (h.bitsperpixel + 7) / 8;
// Bytes per pixel (expanded pixels - not colormap indeces)
if( cmap )
{
bpp2 = (h.cmapentrysize + 7) / 8;
}
else
{
bpp2 = bpp;
}
// For colormaped images, the RGB/RGBA image data may use more memory
// than the stored pixel data
pixsize2 = h.width * h.height * bpp2;
// Allocate memory for pixel data
pix = (unsigned char *) malloc( pixsize2 );
if( pix == NULL )
{
if( cmap )
{
free( cmap );
}
return 0;
}
// Read pixel data from file
if( h.imagetype >= _TGA_IMAGETYPE_CMAP_RLE )
{
ReadTGA_RLE( pix, pixsize, bpp, s );
}
else
{
_glfwReadStream( s, pix, pixsize );
}
// If the image origin is not what we want, re-arrange the pixels
switch( h._origin )
{
default:
case _TGA_ORIGIN_UL:
swapx = 0;
swapy = 1;
break;
case _TGA_ORIGIN_BL:
swapx = 0;
swapy = 0;
break;
case _TGA_ORIGIN_UR:
swapx = 1;
swapy = 1;
break;
case _TGA_ORIGIN_BR:
swapx = 1;
swapy = 0;
break;
}
if( (swapy && !(flags & GLFW_ORIGIN_UL_BIT)) ||
(!swapy && (flags & GLFW_ORIGIN_UL_BIT)) )
{
src = pix;
dst = &pix[ (h.height-1)*h.width*bpp ];
for( n = 0; n < h.height/2; n ++ )
{
for( m = 0; m < h.width ; m ++ )
{
for( k = 0; k < bpp; k ++ )
{
tmp = *src;
*src ++ = *dst;
*dst ++ = tmp;
}
}
dst -= 2*h.width*bpp;
}
}
if( swapx )
{
src = pix;
dst = &pix[ (h.width-1)*bpp ];
for( n = 0; n < h.height; n ++ )
{
for( m = 0; m < h.width/2 ; m ++ )
{
for( k = 0; k < bpp; k ++ )
{
tmp = *src;
*src ++ = *dst;
*dst ++ = tmp;
}
dst -= 2*bpp;
}
src += ((h.width+1)/2)*bpp;
dst += ((3*h.width+1)/2)*bpp;
}
}
// Convert BGR/BGRA to RGB/RGBA, and optionally colormap indeces to
// RGB/RGBA values
if( cmap )
{
// Convert colormap pixel format (BGR -> RGB or BGRA -> RGBA)
if( bpp2 == 3 || bpp2 == 4 )
{
for( n = 0; n < h.cmaplen; n ++ )
{
tmp = cmap[ n*bpp2 ];
cmap[ n*bpp2 ] = cmap[ n*bpp2 + 2 ];
cmap[ n*bpp2 + 2 ] = tmp;
}
}
// Convert pixel data to RGB/RGBA data
for( m = h.width * h.height - 1; m >= 0; m -- )
{
n = pix[ m ];
for( k = 0; k < bpp2; k ++ )
{
pix[ m*bpp2 + k ] = cmap[ n*bpp2 + k ];
}
}
// Free memory for colormap (it's not needed anymore)
free( cmap );
}
else
{
// Convert image pixel format (BGR -> RGB or BGRA -> RGBA)
if( bpp2 == 3 || bpp2 == 4 )
{
src = pix;
dst = &pix[ 2 ];
for( n = 0; n < h.height * h.width; n ++ )
{
tmp = *src;
*src = *dst;
*dst = tmp;
src += bpp2;
dst += bpp2;
}
}
}
// Fill out GLFWimage struct (the Format field will be set by
// glfwReadImage)
img->Width = h.width;
img->Height = h.height;
img->BytesPerPixel = bpp2;
img->Data = pix;
return 1;
}
+341
View File
@@ -0,0 +1,341 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Any
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
//************************************************************************
//**** GLFW internal functions ****
//************************************************************************
//========================================================================
// Find pointer to thread with a matching ID
//========================================================================
_GLFWthread * _glfwGetThreadPointer( int ID )
{
_GLFWthread *t;
for( t = &_glfwThrd.First; t != NULL; t = t->Next )
{
if( t->ID == ID )
{
break;
}
}
return t;
}
//========================================================================
// Append thread to thread list
//========================================================================
void _glfwAppendThread( _GLFWthread * t )
{
_GLFWthread *t_tmp;
t_tmp = &_glfwThrd.First;
while( t_tmp->Next != NULL )
{
t_tmp = t_tmp->Next;
}
t_tmp->Next = t;
t->Previous = t_tmp;
t->Next = NULL;
}
//========================================================================
// Remove thread from thread list
//========================================================================
void _glfwRemoveThread( _GLFWthread * t )
{
if( t->Previous != NULL )
{
t->Previous->Next = t->Next;
}
if( t->Next != NULL )
{
t->Next->Previous = t->Previous;
}
free( (void *) t );
}
//************************************************************************
//**** GLFW user functions ****
//************************************************************************
//========================================================================
// Create a new thread
//========================================================================
GLFWAPI GLFWthread GLFWAPIENTRY glfwCreateThread( GLFWthreadfun fun,
void *arg )
{
// Is GLFW initialized?
if( !_glfwInitialized )
{
return -1;
}
// Return the GLFW thread ID
return _glfwPlatformCreateThread( fun, arg );
}
//========================================================================
// Kill a thread. NOTE: THIS IS A VERY DANGEROUS OPERATION, AND SHOULD NOT
// BE USED EXCEPT IN EXTREME SITUATIONS!
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwDestroyThread( GLFWthread ID )
{
// Is GLFW initialized?
if( !_glfwInitialized )
{
return;
}
// Is it a valid thread? (killing the main thread is not allowed)
if( ID < 1 )
{
return;
}
_glfwPlatformDestroyThread( ID );
}
//========================================================================
// Wait for a thread to die
//========================================================================
GLFWAPI int GLFWAPIENTRY glfwWaitThread( GLFWthread ID, int waitmode )
{
// Is GLFW initialized?
if( !_glfwInitialized )
{
return GL_TRUE;
}
// Is it a valid thread? (waiting for the main thread is not allowed)
if( ID < 1 )
{
return GL_TRUE;
}
return _glfwPlatformWaitThread( ID, waitmode );
}
//========================================================================
// Return the thread ID for the current thread
//========================================================================
GLFWAPI GLFWthread GLFWAPIENTRY glfwGetThreadID( void )
{
// Is GLFW initialized?
if( !_glfwInitialized )
{
return 0;
}
return _glfwPlatformGetThreadID();
}
//========================================================================
// Create a mutual exclusion object
//========================================================================
GLFWAPI GLFWmutex GLFWAPIENTRY glfwCreateMutex( void )
{
// Is GLFW initialized?
if( !_glfwInitialized )
{
return (GLFWmutex) 0;
}
return _glfwPlatformCreateMutex();
}
//========================================================================
// Destroy a mutual exclusion object
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwDestroyMutex( GLFWmutex mutex )
{
// Initialized & valid mutex (no real way of assuring this)?
if( !_glfwInitialized || !mutex )
{
return;
}
_glfwPlatformDestroyMutex( mutex );
}
//========================================================================
// Request access to a mutex
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwLockMutex( GLFWmutex mutex )
{
// Initialized & valid mutex (no real way of assuring this)?
if( !_glfwInitialized && !mutex )
{
return;
}
_glfwPlatformLockMutex( mutex );
}
//========================================================================
// Release a mutex
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwUnlockMutex( GLFWmutex mutex )
{
// Initialized & valid mutex (no real way of assuring this)?
if( !_glfwInitialized && !mutex )
{
return;
}
_glfwPlatformUnlockMutex( mutex );
}
//========================================================================
// Create a new condition variable object
//========================================================================
GLFWAPI GLFWcond GLFWAPIENTRY glfwCreateCond( void )
{
// Is GLFW initialized?
if( !_glfwInitialized )
{
return (GLFWcond) 0;
}
return _glfwPlatformCreateCond();
}
//========================================================================
// Destroy a condition variable object
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwDestroyCond( GLFWcond cond )
{
// Initialized & valid condition variable?
if( !_glfwInitialized || !cond )
{
return;
}
_glfwPlatformDestroyCond( cond );
}
//========================================================================
// Wait for a condition to be raised
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwWaitCond( GLFWcond cond, GLFWmutex mutex,
double timeout )
{
// Initialized & valid condition variable and mutex?
if( !_glfwInitialized || !cond || !mutex )
{
return;
}
_glfwPlatformWaitCond( cond, mutex, timeout );
}
//========================================================================
// Signal a condition to one waiting thread
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwSignalCond( GLFWcond cond )
{
// Initialized & valid condition variable?
if( !_glfwInitialized || !cond )
{
return;
}
_glfwPlatformSignalCond( cond );
}
//========================================================================
// Broadcast a condition to all waiting threads
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwBroadcastCond( GLFWcond cond )
{
// Initialized & valid condition variable?
if( !_glfwInitialized || !cond )
{
return;
}
_glfwPlatformBroadcastCond( cond );
}
//========================================================================
// Return the number of processors in the system. This information can be
// useful for determining the optimal number of threads to use for
// performing a certain task.
//========================================================================
GLFWAPI int GLFWAPIENTRY glfwGetNumberOfProcessors( void )
{
// Is GLFW initialized?
if( !_glfwInitialized )
{
return 0;
}
return _glfwPlatformGetNumberOfProcessors();
}
+84
View File
@@ -0,0 +1,84 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Any
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
//************************************************************************
//**** GLFW user functions ****
//************************************************************************
//========================================================================
// Return timer value in seconds
//========================================================================
GLFWAPI double GLFWAPIENTRY glfwGetTime( void )
{
// Is GLFW initialized?
if( !_glfwInitialized )
{
return 0.0;
}
return _glfwPlatformGetTime();
}
//========================================================================
// Set timer value in seconds
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwSetTime( double time )
{
// Is GLFW initialized?
if( !_glfwInitialized )
{
return;
}
_glfwPlatformSetTime( time );
}
//========================================================================
// Put a thread to sleep for a specified amount of time
//========================================================================
GLFWAPI void GLFWAPIENTRY glfwSleep( double time )
{
// Is GLFW initialized?
if( !_glfwInitialized )
{
return;
}
_glfwPlatformSleep( time );
}
+558
View File
@@ -0,0 +1,558 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Win32/WGL
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#ifndef _platform_h_
#define _platform_h_
// This is the Windows version of GLFW
#define _GLFW_WIN32
// We don't need all the fancy stuff
#define NOMINMAX
#define WIN32_LEAN_AND_MEAN
#define VC_EXTRALEAN
// Include files
#include <windows.h>
#include <mmsystem.h>
#include "../../include/GL/glfw.h"
//========================================================================
// Hack: Define things that some <windows.h>'s do not define
//========================================================================
// Some old versions of w32api (used by MinGW and Cygwin) define
// WH_KEYBOARD_LL without typedef:ing KBDLLHOOKSTRUCT (!)
#if defined(__MINGW32__) || defined(__CYGWIN__)
#include <w32api.h>
#if defined(WH_KEYBOARD_LL) && (__W32API_MAJOR_VERSION == 1) && (__W32API_MINOR_VERSION <= 2)
#undef WH_KEYBOARD_LL
#endif
#endif
//------------------------------------------------------------------------
// ** NOTE ** If this gives you compiler errors and you are using MinGW
// (or Dev-C++), update to w32api version 1.3 or later:
// http://sourceforge.net/project/showfiles.php?group_id=2435
//------------------------------------------------------------------------
#ifndef WH_KEYBOARD_LL
#define WH_KEYBOARD_LL 13
typedef struct tagKBDLLHOOKSTRUCT {
DWORD vkCode;
DWORD scanCode;
DWORD flags;
DWORD time;
DWORD dwExtraInfo;
} KBDLLHOOKSTRUCT, FAR *LPKBDLLHOOKSTRUCT, *PKBDLLHOOKSTRUCT;
#endif // WH_KEYBOARD_LL
#ifndef LLKHF_ALTDOWN
#define LLKHF_ALTDOWN 0x00000020
#endif
#ifndef SPI_SETSCREENSAVERRUNNING
#define SPI_SETSCREENSAVERRUNNING 97
#endif
#ifndef SPI_GETANIMATION
#define SPI_GETANIMATION 72
#endif
#ifndef SPI_SETANIMATION
#define SPI_SETANIMATION 73
#endif
#ifndef SPI_GETFOREGROUNDLOCKTIMEOUT
#define SPI_GETFOREGROUNDLOCKTIMEOUT 0x2000
#endif
#ifndef SPI_SETFOREGROUNDLOCKTIMEOUT
#define SPI_SETFOREGROUNDLOCKTIMEOUT 0x2001
#endif
#ifndef CDS_FULLSCREEN
#define CDS_FULLSCREEN 4
#endif
#ifndef PFD_GENERIC_ACCELERATED
#define PFD_GENERIC_ACCELERATED 0x00001000
#endif
#ifndef PFD_DEPTH_DONTCARE
#define PFD_DEPTH_DONTCARE 0x20000000
#endif
#ifndef ENUM_CURRENT_SETTINGS
#define ENUM_CURRENT_SETTINGS -1
#endif
#ifndef ENUM_REGISTRY_SETTINGS
#define ENUM_REGISTRY_SETTINGS -2
#endif
#ifndef WM_MOUSEWHEEL
#define WM_MOUSEWHEEL 0x020A
#endif
#ifndef WHEEL_DELTA
#define WHEEL_DELTA 120
#endif
#ifndef WM_XBUTTONDOWN
#define WM_XBUTTONDOWN 0x020B
#endif
#ifndef WM_XBUTTONUP
#define WM_XBUTTONUP 0x020C
#endif
#ifndef XBUTTON1
#define XBUTTON1 1
#endif
#ifndef XBUTTON2
#define XBUTTON2 2
#endif
#ifndef WGL_EXT_swap_control
/* Entry points */
typedef int (APIENTRY * PFNWGLSWAPINTERVALEXTPROC) (int);
#endif /*WGL_EXT_swap_control*/
#ifndef WGL_ARB_extensions_string
/* Entry points */
typedef const char *(APIENTRY * PFNWGLGETEXTENSIONSSTRINGARBPROC)( HDC );
#endif /*WGL_ARB_extensions_string*/
#ifndef WGL_EXT_extension_string
/* Entry points */
typedef const char *(APIENTRY * PFNWGLGETEXTENSIONSSTRINGEXTPROC)( void );
#endif /*WGL_EXT_extension_string*/
#ifndef WGL_ARB_pixel_format
/* Entry points */
typedef BOOL (WINAPI * PFNWGLGETPIXELFORMATATTRIBIVARBPROC) (HDC, int, int, UINT, const int *, int *);
/* Constants for wglGetPixelFormatAttribivARB */
#define WGL_NUMBER_PIXEL_FORMATS_ARB 0x2000
#define WGL_DRAW_TO_WINDOW_ARB 0x2001
#define WGL_SUPPORT_OPENGL_ARB 0x2010
#define WGL_ACCELERATION_ARB 0x2003
#define WGL_DOUBLE_BUFFER_ARB 0x2011
#define WGL_STEREO_ARB 0x2012
#define WGL_PIXEL_TYPE_ARB 0x2013
#define WGL_COLOR_BITS_ARB 0x2014
#define WGL_RED_BITS_ARB 0x2015
#define WGL_GREEN_BITS_ARB 0x2017
#define WGL_BLUE_BITS_ARB 0x2019
#define WGL_ALPHA_BITS_ARB 0x201B
#define WGL_ACCUM_BITS_ARB 0x201D
#define WGL_ACCUM_RED_BITS_ARB 0x201E
#define WGL_ACCUM_GREEN_BITS_ARB 0x201F
#define WGL_ACCUM_BLUE_BITS_ARB 0x2020
#define WGL_ACCUM_ALPHA_BITS_ARB 0x2021
#define WGL_DEPTH_BITS_ARB 0x2022
#define WGL_STENCIL_BITS_ARB 0x2023
#define WGL_AUX_BUFFERS_ARB 0x2024
#define WGL_SAMPLE_BUFFERS_ARB 0x2041
#define WGL_SAMPLES_ARB 0x2042
/* Constants for WGL_ACCELERATION_ARB */
#define WGL_NO_ACCELERATION_ARB 0x2025
#define WGL_GENERIC_ACCELERATION_ARB 0x2026
#define WGL_FULL_ACCELERATION_ARB 0x2027
/* Constants for WGL_PIXEL_TYPE_ARB */
#define WGL_TYPE_RGBA_ARB 0x202B
#define WGL_TYPE_COLORINDEX_ARB 0x202C
#endif /*WGL_ARB_pixel_format*/
#ifndef WGL_ARB_create_context
/* Entry points */
typedef HGLRC (WINAPI * PFNWGLCREATECONTEXTATTRIBSARBPROC) (HDC, HGLRC, const int *);
/* Tokens for wglCreateContextAttribsARB attributes */
#define WGL_CONTEXT_MAJOR_VERSION_ARB 0x2091
#define WGL_CONTEXT_MINOR_VERSION_ARB 0x2092
#define WGL_CONTEXT_LAYER_PLANE_ARB 0x2093
#define WGL_CONTEXT_FLAGS_ARB 0x2094
#define WGL_CONTEXT_PROFILE_MASK_ARB 0x9126
/* Bits for WGL_CONTEXT_FLAGS_ARB */
#define WGL_CONTEXT_DEBUG_BIT_ARB 0x0001
#define WGL_CONTEXT_FORWARD_COMPATIBLE_BIT_ARB 0x0002
/* Bits for WGL_CONTEXT_PROFILE_MASK_ARB */
#define WGL_CONTEXT_CORE_PROFILE_BIT_ARB 0x00000001
#define WGL_CONTEXT_COMPATIBILITY_PROFILE_BIT_ARB 0x00000002
#endif /*WGL_ARB_create_context*/
#ifndef GL_VERSION_3_0
typedef const GLubyte * (APIENTRY *PFNGLGETSTRINGIPROC) (GLenum, GLuint);
#endif /*GL_VERSION_3_0*/
//========================================================================
// DLLs that are loaded at glfwInit()
//========================================================================
// gdi32.dll function pointer typedefs
#ifndef _GLFW_NO_DLOAD_GDI32
typedef int (WINAPI * CHOOSEPIXELFORMAT_T) (HDC,CONST PIXELFORMATDESCRIPTOR*);
typedef int (WINAPI * DESCRIBEPIXELFORMAT_T) (HDC,int,UINT,LPPIXELFORMATDESCRIPTOR);
typedef int (WINAPI * GETPIXELFORMAT_T) (HDC);
typedef BOOL (WINAPI * SETPIXELFORMAT_T) (HDC,int,const PIXELFORMATDESCRIPTOR*);
typedef BOOL (WINAPI * SWAPBUFFERS_T) (HDC);
#endif // _GLFW_NO_DLOAD_GDI32
// winmm.dll function pointer typedefs
#ifndef _GLFW_NO_DLOAD_WINMM
typedef MMRESULT (WINAPI * JOYGETDEVCAPSA_T) (UINT,LPJOYCAPSA,UINT);
typedef MMRESULT (WINAPI * JOYGETPOS_T) (UINT,LPJOYINFO);
typedef MMRESULT (WINAPI * JOYGETPOSEX_T) (UINT,LPJOYINFOEX);
typedef DWORD (WINAPI * TIMEGETTIME_T) (void);
#endif // _GLFW_NO_DLOAD_WINMM
// gdi32.dll shortcuts
#ifndef _GLFW_NO_DLOAD_GDI32
#define _glfw_ChoosePixelFormat _glfwLibrary.Libs.ChoosePixelFormat
#define _glfw_DescribePixelFormat _glfwLibrary.Libs.DescribePixelFormat
#define _glfw_GetPixelFormat _glfwLibrary.Libs.GetPixelFormat
#define _glfw_SetPixelFormat _glfwLibrary.Libs.SetPixelFormat
#define _glfw_SwapBuffers _glfwLibrary.Libs.SwapBuffers
#else
#define _glfw_ChoosePixelFormat ChoosePixelFormat
#define _glfw_DescribePixelFormat DescribePixelFormat
#define _glfw_GetPixelFormat GetPixelFormat
#define _glfw_SetPixelFormat SetPixelFormat
#define _glfw_SwapBuffers SwapBuffers
#endif // _GLFW_NO_DLOAD_GDI32
// winmm.dll shortcuts
#ifndef _GLFW_NO_DLOAD_WINMM
#define _glfw_joyGetDevCaps _glfwLibrary.Libs.joyGetDevCapsA
#define _glfw_joyGetPos _glfwLibrary.Libs.joyGetPos
#define _glfw_joyGetPosEx _glfwLibrary.Libs.joyGetPosEx
#define _glfw_timeGetTime _glfwLibrary.Libs.timeGetTime
#else
#define _glfw_joyGetDevCaps joyGetDevCapsA
#define _glfw_joyGetPos joyGetPos
#define _glfw_joyGetPosEx joyGetPosEx
#define _glfw_timeGetTime timeGetTime
#endif // _GLFW_NO_DLOAD_WINMM
//========================================================================
// GLFW platform specific types
//========================================================================
//------------------------------------------------------------------------
// Pointer length integer
//------------------------------------------------------------------------
typedef INT_PTR GLFWintptr;
//------------------------------------------------------------------------
// Window structure
//------------------------------------------------------------------------
typedef struct _GLFWwin_struct _GLFWwin;
struct _GLFWwin_struct {
// ========= PLATFORM INDEPENDENT MANDATORY PART =========================
// User callback functions
GLFWwindowsizefun windowSizeCallback;
GLFWwindowclosefun windowCloseCallback;
GLFWwindowrefreshfun windowRefreshCallback;
GLFWmousebuttonfun mouseButtonCallback;
GLFWmouseposfun mousePosCallback;
GLFWmousewheelfun mouseWheelCallback;
GLFWkeyfun keyCallback;
GLFWcharfun charCallback;
// User selected window settings
int fullscreen; // Fullscreen flag
int mouseLock; // Mouse-lock flag
int autoPollEvents; // Auto polling flag
int sysKeysDisabled; // System keys disabled flag
int windowNoResize; // Resize- and maximize gadgets disabled flag
int refreshRate; // Vertical monitor refresh rate
// Window status & parameters
int opened; // Flag telling if window is opened or not
int active; // Application active flag
int iconified; // Window iconified flag
int width, height; // Window width and heigth
int accelerated; // GL_TRUE if window is HW accelerated
// Framebuffer attributes
int redBits;
int greenBits;
int blueBits;
int alphaBits;
int depthBits;
int stencilBits;
int accumRedBits;
int accumGreenBits;
int accumBlueBits;
int accumAlphaBits;
int auxBuffers;
int stereo;
int samples;
// OpenGL extensions and context attributes
int has_GL_SGIS_generate_mipmap;
int has_GL_ARB_texture_non_power_of_two;
int glMajor, glMinor, glRevision;
int glForward, glDebug, glProfile;
PFNGLGETSTRINGIPROC GetStringi;
// ========= PLATFORM SPECIFIC PART ======================================
// Platform specific window resources
HDC DC; // Private GDI device context
HGLRC context; // Permanent rendering context
HWND window; // Window handle
ATOM classAtom; // Window class atom
int modeID; // Mode ID for fullscreen mode
HHOOK keyboardHook; // Keyboard hook handle
DWORD dwStyle; // Window styles used for window creation
DWORD dwExStyle; // --"--
// Platform specific extensions (context specific)
PFNWGLSWAPINTERVALEXTPROC SwapIntervalEXT;
PFNWGLGETPIXELFORMATATTRIBIVARBPROC GetPixelFormatAttribivARB;
PFNWGLGETEXTENSIONSSTRINGEXTPROC GetExtensionsStringEXT;
PFNWGLGETEXTENSIONSSTRINGARBPROC GetExtensionsStringARB;
PFNWGLCREATECONTEXTATTRIBSARBPROC CreateContextAttribsARB;
GLboolean has_WGL_EXT_swap_control;
GLboolean has_WGL_ARB_multisample;
GLboolean has_WGL_ARB_pixel_format;
GLboolean has_WGL_ARB_create_context;
GLboolean has_WGL_ARB_create_context_profile;
// Various platform specific internal variables
int oldMouseLock; // Old mouse-lock flag (used for remembering
// mouse-lock state when iconifying)
int oldMouseLockValid;
int desiredRefreshRate; // Desired vertical monitor refresh rate
};
GLFWGLOBAL _GLFWwin _glfwWin;
//------------------------------------------------------------------------
// User input status (most of this should go in _GLFWwin)
//------------------------------------------------------------------------
GLFWGLOBAL struct {
// ========= PLATFORM INDEPENDENT MANDATORY PART =========================
// Mouse status
int MousePosX, MousePosY;
int WheelPos;
char MouseButton[ GLFW_MOUSE_BUTTON_LAST+1 ];
// Keyboard status
char Key[ GLFW_KEY_LAST+1 ];
int LastChar;
// User selected settings
int StickyKeys;
int StickyMouseButtons;
int KeyRepeat;
// ========= PLATFORM SPECIFIC PART ======================================
// Platform specific internal variables
int MouseMoved, OldMouseX, OldMouseY;
} _glfwInput;
//------------------------------------------------------------------------
// Library global data
//------------------------------------------------------------------------
GLFWGLOBAL struct {
// Window opening hints
_GLFWhints hints;
// Initial desktop mode
GLFWvidmode desktopMode;
// ========= PLATFORM SPECIFIC PART ======================================
HINSTANCE instance; // Instance of the application
// Timer data
struct {
int HasPerformanceCounter;
double Resolution;
unsigned int t0_32;
__int64 t0_64;
} Timer;
// System information
struct {
int winVer;
int hasUnicode;
DWORD foregroundLockTimeout;
} Sys;
#if !defined(_GLFW_NO_DLOAD_WINMM) || !defined(_GLFW_NO_DLOAD_GDI32)
// Library handles and function pointers
struct {
#ifndef _GLFW_NO_DLOAD_GDI32
// gdi32.dll
HINSTANCE gdi32;
CHOOSEPIXELFORMAT_T ChoosePixelFormat;
DESCRIBEPIXELFORMAT_T DescribePixelFormat;
GETPIXELFORMAT_T GetPixelFormat;
SETPIXELFORMAT_T SetPixelFormat;
SWAPBUFFERS_T SwapBuffers;
#endif // _GLFW_NO_DLOAD_GDI32
// winmm.dll
#ifndef _GLFW_NO_DLOAD_WINMM
HINSTANCE winmm;
JOYGETDEVCAPSA_T joyGetDevCapsA;
JOYGETPOS_T joyGetPos;
JOYGETPOSEX_T joyGetPosEx;
TIMEGETTIME_T timeGetTime;
#endif // _GLFW_NO_DLOAD_WINMM
} Libs;
#endif
} _glfwLibrary;
//------------------------------------------------------------------------
// Thread record (one for each thread)
//------------------------------------------------------------------------
typedef struct _GLFWthread_struct _GLFWthread;
struct _GLFWthread_struct {
// ========= PLATFORM INDEPENDENT MANDATORY PART =========================
// Pointer to previous and next threads in linked list
_GLFWthread *Previous, *Next;
// GLFW user side thread information
GLFWthread ID;
GLFWthreadfun Function;
// ========= PLATFORM SPECIFIC PART ======================================
// System side thread information
HANDLE Handle;
DWORD WinID;
};
//------------------------------------------------------------------------
// General thread information
//------------------------------------------------------------------------
GLFWGLOBAL struct {
// ========= PLATFORM INDEPENDENT MANDATORY PART =========================
// Next thread ID to use (increments for every created thread)
GLFWthread NextID;
// First thread in linked list (always the main thread)
_GLFWthread First;
// ========= PLATFORM SPECIFIC PART ======================================
// Critical section lock
CRITICAL_SECTION CriticalSection;
} _glfwThrd;
//========================================================================
// Macros for encapsulating critical code sections (i.e. making parts
// of GLFW thread safe)
//========================================================================
// Thread list management
#define ENTER_THREAD_CRITICAL_SECTION \
EnterCriticalSection( &_glfwThrd.CriticalSection );
#define LEAVE_THREAD_CRITICAL_SECTION \
LeaveCriticalSection( &_glfwThrd.CriticalSection );
//========================================================================
// Various Windows version constants
//========================================================================
#define _GLFW_WIN_UNKNOWN 0x0000 // Earlier than 95 or NT4
#define _GLFW_WIN_95 0x0001
#define _GLFW_WIN_98 0x0002
#define _GLFW_WIN_ME 0x0003
#define _GLFW_WIN_UNKNOWN_9x 0x0004 // Later than ME
#define _GLFW_WIN_NT4 0x0101
#define _GLFW_WIN_2K 0x0102
#define _GLFW_WIN_XP 0x0103
#define _GLFW_WIN_NET_SERVER 0x0104
#define _GLFW_WIN_UNKNOWN_NT 0x0105 // Later than .NET Server
//========================================================================
// Prototypes for platform specific internal functions
//========================================================================
// Time
void _glfwInitTimer( void );
// Fullscreen support
int _glfwGetClosestVideoModeBPP( int *w, int *h, int *bpp, int *refresh );
int _glfwGetClosestVideoMode( int *w, int *h, int *r, int *g, int *b, int *refresh );
void _glfwSetVideoModeMODE( int mode );
void _glfwSetVideoMode( int *w, int *h, int r, int g, int b, int refresh );
#endif // _platform_h_
@@ -0,0 +1,49 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Win32/WGL
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
#if defined(GLFW_BUILD_DLL)
//========================================================================
// GLFW DLL entry point
//========================================================================
BOOL WINAPI DllMain( HINSTANCE instance, DWORD reason, LPVOID reserved )
{
// NOTE: Some compilers complains about instance and x never being used -
// never mind that (we don't want to use them)!
return TRUE;
}
#endif // GLFW_BUILD_DLL
@@ -0,0 +1,155 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Win32/WGL
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
//************************************************************************
//**** GLFW internal functions ****
//************************************************************************
//========================================================================
// Low level keyboard hook (system callback) function
// Used to disable system keys under Windows NT
//========================================================================
static LRESULT CALLBACK keyboardHook( int nCode, WPARAM wParam, LPARAM lParam )
{
BOOL syskeys = FALSE;
PKBDLLHOOKSTRUCT p;
// We are only looking for keyboard events - interpret lParam as a
// pointer to a KBDLLHOOKSTRUCT
p = (PKBDLLHOOKSTRUCT) lParam;
if( nCode == HC_ACTION )
{
// We have a keyboard event
switch( wParam )
{
case WM_KEYDOWN:
case WM_SYSKEYDOWN:
case WM_KEYUP:
case WM_SYSKEYUP:
// Detect: ALT+TAB, ALT+ESC, ALT+F4, CTRL+ESC,
// LWIN, RWIN, APPS (mysterious menu key)
syskeys = ( p->vkCode == VK_TAB &&
p->flags & LLKHF_ALTDOWN ) ||
( p->vkCode == VK_ESCAPE &&
p->flags & LLKHF_ALTDOWN ) ||
( p->vkCode == VK_F4 &&
p->flags & LLKHF_ALTDOWN ) ||
( p->vkCode == VK_ESCAPE &&
(GetKeyState(VK_CONTROL) & 0x8000)) ||
p->vkCode == VK_LWIN ||
p->vkCode == VK_RWIN ||
p->vkCode == VK_APPS;
break;
default:
break;
}
}
// Was it a system key combination (e.g. ALT+TAB)?
if( syskeys )
{
// Pass the key event to our window message loop
if( _glfwWin.opened )
{
PostMessage( _glfwWin.window, (UINT) wParam, p->vkCode, 0 );
}
// We've taken care of it - don't let the system know about this
// key event
return 1;
}
else
{
// It's a harmless key press, let the system deal with it
return CallNextHookEx( _glfwWin.keyboardHook, nCode, wParam, lParam );
}
}
//************************************************************************
//**** Platform implementation functions ****
//************************************************************************
//========================================================================
// Enable system keys
//========================================================================
void _glfwPlatformEnableSystemKeys( void )
{
BOOL dummy;
// Use different methods depending on operating system version
if( _glfwLibrary.Sys.winVer >= _GLFW_WIN_NT4 )
{
if( _glfwWin.keyboardHook != NULL )
{
UnhookWindowsHookEx( _glfwWin.keyboardHook );
_glfwWin.keyboardHook = NULL;
}
}
else
{
(void) SystemParametersInfo( SPI_SETSCREENSAVERRUNNING, FALSE, &dummy, 0 );
}
}
//========================================================================
// Disable system keys
//========================================================================
void _glfwPlatformDisableSystemKeys( void )
{
BOOL dummy;
// Use different methods depending on operating system version
if( _glfwLibrary.Sys.winVer >= _GLFW_WIN_NT4 )
{
// Under Windows NT, install a low level keyboard hook
_glfwWin.keyboardHook = SetWindowsHookEx( WH_KEYBOARD_LL,
keyboardHook,
_glfwLibrary.instance,
0 );
}
else
{
// Under Windows 95/98/ME, fool Windows that a screensaver
// is running => prevents ALT+TAB, CTRL+ESC and CTRL+ALT+DEL
(void) SystemParametersInfo( SPI_SETSCREENSAVERRUNNING, TRUE, &dummy, 0 );
}
}
@@ -0,0 +1,320 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Win32/WGL
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
//************************************************************************
//**** GLFW internal functions ****
//************************************************************************
//========================================================================
// Convert BPP to RGB bits based on "best guess"
//========================================================================
static void bpp2rgb( int bpp, int *r, int *g, int *b )
{
int delta;
// We assume that by 32 they really meant 24
if( bpp == 32 )
{
bpp = 24;
}
// Convert "bits per pixel" to red, green & blue sizes
*r = *g = *b = bpp / 3;
delta = bpp - (*r * 3);
if( delta >= 1 )
{
*g = *g + 1;
}
if( delta == 2 )
{
*r = *r + 1;
}
}
//========================================================================
// Return closest video mode by dimensions, refresh rate and bits per pixel
//========================================================================
int _glfwGetClosestVideoModeBPP( int *w, int *h, int *bpp, int *refresh )
{
int mode, bestmode, match, bestmatch, rr, bestrr, success;
DEVMODE dm;
// Find best match
bestmatch = 0x7fffffff;
bestrr = 0x7fffffff;
mode = bestmode = 0;
do
{
dm.dmSize = sizeof( DEVMODE );
success = EnumDisplaySettings( NULL, mode, &dm );
if( success )
{
match = dm.dmBitsPerPel - *bpp;
if( match < 0 ) match = -match;
match = ( match << 25 ) |
( (dm.dmPelsWidth - *w) *
(dm.dmPelsWidth - *w) +
(dm.dmPelsHeight - *h) *
(dm.dmPelsHeight - *h) );
if( match < bestmatch )
{
bestmatch = match;
bestmode = mode;
bestrr = (dm.dmDisplayFrequency - *refresh) *
(dm.dmDisplayFrequency - *refresh);
}
else if( match == bestmatch && *refresh > 0 )
{
rr = (dm.dmDisplayFrequency - *refresh) *
(dm.dmDisplayFrequency - *refresh);
if( rr < bestrr )
{
bestmatch = match;
bestmode = mode;
bestrr = rr;
}
}
}
mode ++;
}
while( success );
// Get the parameters for the best matching display mode
dm.dmSize = sizeof( DEVMODE );
(void) EnumDisplaySettings( NULL, bestmode, &dm );
// Fill out actual width and height
*w = dm.dmPelsWidth;
*h = dm.dmPelsHeight;
// Return bits per pixel
*bpp = dm.dmBitsPerPel;
// Return vertical refresh rate
*refresh = dm.dmDisplayFrequency;
return bestmode;
}
//========================================================================
// Return closest video mode by dimensions, refresh rate and channel sizes
//========================================================================
static int getClosestVideoMode( int *w, int *h,
int *r, int *g, int *b,
int *refresh )
{
int bpp, bestmode;
// Colorbits = sum of red/green/blue bits
bpp = *r + *g + *b;
// If colorbits < 15 (e.g. 0) or >= 24, default to 32 bpp
if( bpp < 15 || bpp >= 24 )
{
bpp = 32;
}
// Find best match
bestmode = _glfwGetClosestVideoModeBPP( w, h, &bpp, refresh );
// Convert "bits per pixel" to red, green & blue sizes
bpp2rgb( bpp, r, g, b );
return bestmode;
}
//========================================================================
// Change the current video mode
//========================================================================
void _glfwSetVideoModeMODE( int mode )
{
DEVMODE dm;
int success;
// Get the parameters for the best matching display mode
dm.dmSize = sizeof( DEVMODE );
(void) EnumDisplaySettings( NULL, mode, &dm );
// Set which fields we want to specify
dm.dmFields = DM_PELSWIDTH | DM_PELSHEIGHT | DM_BITSPERPEL;
// Do we have a prefered refresh rate?
if( _glfwWin.desiredRefreshRate > 0 )
{
dm.dmFields = dm.dmFields | DM_DISPLAYFREQUENCY;
dm.dmDisplayFrequency = _glfwWin.desiredRefreshRate;
}
// Change display setting
dm.dmSize = sizeof( DEVMODE );
success = ChangeDisplaySettings( &dm, CDS_FULLSCREEN );
// If the mode change was not possible, query the current display
// settings (we'll use the desktop resolution for fullscreen mode)
if( success == DISP_CHANGE_SUCCESSFUL )
{
_glfwWin.modeID = mode;
}
else
{
_glfwWin.modeID = ENUM_REGISTRY_SETTINGS;
EnumDisplaySettings( NULL, ENUM_REGISTRY_SETTINGS, &dm );
}
// Set the window size to that of the display mode
_glfwWin.width = dm.dmPelsWidth;
_glfwWin.height = dm.dmPelsHeight;
}
//========================================================================
// Change the current video mode
//========================================================================
void _glfwSetVideoMode( int *w, int *h, int r, int g, int b, int refresh )
{
int bestmode;
// Find a best match mode
bestmode = getClosestVideoMode( w, h, &r, &g, &b, &refresh );
// Change mode
_glfwSetVideoModeMODE( bestmode );
}
//************************************************************************
//**** GLFW user functions ****
//************************************************************************
//========================================================================
// Get a list of available video modes
//========================================================================
int _glfwPlatformGetVideoModes( GLFWvidmode *list, int maxcount )
{
int count, success, mode, i, j;
int m1 = 0, m2 = 0, bpp, r, g, b;
DEVMODE dm;
// Loop through all video modes and extract all the UNIQUE modes
count = 0;
mode = 0;
do
{
// Get video mode properties
dm.dmSize = sizeof( DEVMODE );
success = EnumDisplaySettings( NULL, mode, &dm );
// Is it a valid mode? (only list depths >= 15 bpp)
if( success && dm.dmBitsPerPel >= 15 )
{
// Convert to RGB, and back to bpp ("mask out" alpha bits etc)
bpp2rgb( dm.dmBitsPerPel, &r, &g, &b );
bpp = r + g + b;
// Mode "code" for this mode
m1 = (bpp << 25) | (dm.dmPelsWidth * dm.dmPelsHeight);
// Insert mode in list (sorted), and avoid duplicates
for( i = 0; i < count; i ++ )
{
// Mode "code" for already listed mode
bpp = list[i].RedBits + list[i].GreenBits +
list[i].BlueBits;
m2 = (bpp << 25) | (list[i].Width * list[i].Height);
if( m1 <= m2 )
{
break;
}
}
// New entry at the end of the list?
if( i >= count )
{
list[count].Width = dm.dmPelsWidth;
list[count].Height = dm.dmPelsHeight;
list[count].RedBits = r;
list[count].GreenBits = g;
list[count].BlueBits = b;
count ++;
}
// Insert new entry in the list?
else if( m1 < m2 )
{
for( j = count; j > i; j -- )
{
list[j] = list[j-1];
}
list[i].Width = dm.dmPelsWidth;
list[i].Height = dm.dmPelsHeight;
list[i].RedBits = r;
list[i].GreenBits = g;
list[i].BlueBits = b;
count ++;
}
}
mode ++;
}
while( success && (count < maxcount) );
return count;
}
//========================================================================
// Get the desktop video mode
//========================================================================
void _glfwPlatformGetDesktopMode( GLFWvidmode *mode )
{
DEVMODE dm;
// Get desktop display mode
dm.dmSize = sizeof( DEVMODE );
(void) EnumDisplaySettings( NULL, ENUM_REGISTRY_SETTINGS, &dm );
// Return desktop mode parameters
mode->Width = dm.dmPelsWidth;
mode->Height = dm.dmPelsHeight;
bpp2rgb( dm.dmBitsPerPel, &mode->RedBits, &mode->GreenBits, &mode->BlueBits );
}
@@ -0,0 +1,85 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Win32/WGL
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
#ifdef _MSC_VER
#pragma warning(disable:4054) // A function pointer is cast to a data pointer.
#endif // _MSC8VER
//************************************************************************
//**** Platform implementation functions ****
//************************************************************************
//========================================================================
// Check if the current context supports the specified WGL extension
//========================================================================
int _glfwPlatformExtensionSupported( const char *extension )
{
const GLubyte *extensions;
if( _glfwWin.GetExtensionsStringEXT != NULL )
{
extensions = (GLubyte *) _glfwWin.GetExtensionsStringEXT();
if( extensions != NULL )
{
if( _glfwStringInExtensionString( extension, extensions ) )
{
return GL_TRUE;
}
}
}
if( _glfwWin.GetExtensionsStringARB != NULL )
{
extensions = (GLubyte *) _glfwWin.GetExtensionsStringARB( _glfwWin.DC );
if( extensions != NULL )
{
if( _glfwStringInExtensionString( extension, extensions ) )
{
return GL_TRUE;
}
}
}
return GL_FALSE;
}
//========================================================================
// Get the function pointer to an OpenGL function
//========================================================================
void *_glfwPlatformGetProcAddress( const char *procname )
{
return (void *) wglGetProcAddress( procname );
}
@@ -0,0 +1,364 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Win32/WGL
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
// With the Borland C++ compiler, we want to disable FPU exceptions
#ifdef __BORLANDC__
#include <float.h>
#endif // __BORLANDC__
//************************************************************************
//**** GLFW internal functions ****
//************************************************************************
//========================================================================
// Load necessary libraries (DLLs)
//========================================================================
static int _glfwInitLibraries( void )
{
// gdi32.dll (OpenGL pixel format functions & SwapBuffers)
#ifndef _GLFW_NO_DLOAD_GDI32
_glfwLibrary.Libs.gdi32 = LoadLibrary( "gdi32.dll" );
if( _glfwLibrary.Libs.gdi32 != NULL )
{
_glfwLibrary.Libs.ChoosePixelFormat = (CHOOSEPIXELFORMAT_T)
GetProcAddress( _glfwLibrary.Libs.gdi32, "ChoosePixelFormat" );
_glfwLibrary.Libs.DescribePixelFormat = (DESCRIBEPIXELFORMAT_T)
GetProcAddress( _glfwLibrary.Libs.gdi32, "DescribePixelFormat" );
_glfwLibrary.Libs.GetPixelFormat = (GETPIXELFORMAT_T)
GetProcAddress( _glfwLibrary.Libs.gdi32, "GetPixelFormat" );
_glfwLibrary.Libs.SetPixelFormat = (SETPIXELFORMAT_T)
GetProcAddress( _glfwLibrary.Libs.gdi32, "SetPixelFormat" );
_glfwLibrary.Libs.SwapBuffers = (SWAPBUFFERS_T)
GetProcAddress( _glfwLibrary.Libs.gdi32, "SwapBuffers" );
if( _glfwLibrary.Libs.ChoosePixelFormat == NULL ||
_glfwLibrary.Libs.DescribePixelFormat == NULL ||
_glfwLibrary.Libs.GetPixelFormat == NULL ||
_glfwLibrary.Libs.SetPixelFormat == NULL ||
_glfwLibrary.Libs.SwapBuffers == NULL )
{
FreeLibrary( _glfwLibrary.Libs.gdi32 );
_glfwLibrary.Libs.gdi32 = NULL;
return GL_FALSE;
}
}
else
{
return GL_FALSE;
}
#endif // _GLFW_NO_DLOAD_GDI32
// winmm.dll (for joystick and timer support)
#ifndef _GLFW_NO_DLOAD_WINMM
_glfwLibrary.Libs.winmm = LoadLibrary( "winmm.dll" );
if( _glfwLibrary.Libs.winmm != NULL )
{
_glfwLibrary.Libs.joyGetDevCapsA = (JOYGETDEVCAPSA_T)
GetProcAddress( _glfwLibrary.Libs.winmm, "joyGetDevCapsA" );
_glfwLibrary.Libs.joyGetPos = (JOYGETPOS_T)
GetProcAddress( _glfwLibrary.Libs.winmm, "joyGetPos" );
_glfwLibrary.Libs.joyGetPosEx = (JOYGETPOSEX_T)
GetProcAddress( _glfwLibrary.Libs.winmm, "joyGetPosEx" );
_glfwLibrary.Libs.timeGetTime = (TIMEGETTIME_T)
GetProcAddress( _glfwLibrary.Libs.winmm, "timeGetTime" );
if( _glfwLibrary.Libs.joyGetDevCapsA == NULL ||
_glfwLibrary.Libs.joyGetPos == NULL ||
_glfwLibrary.Libs.joyGetPosEx == NULL ||
_glfwLibrary.Libs.timeGetTime == NULL )
{
FreeLibrary( _glfwLibrary.Libs.winmm );
_glfwLibrary.Libs.winmm = NULL;
return GL_FALSE;
}
}
else
{
return GL_FALSE;
}
#endif // _GLFW_NO_DLOAD_WINMM
return GL_TRUE;
}
//========================================================================
// Unload used libraries (DLLs)
//========================================================================
static void _glfwFreeLibraries( void )
{
// gdi32.dll
#ifndef _GLFW_NO_DLOAD_GDI32
if( _glfwLibrary.Libs.gdi32 != NULL )
{
FreeLibrary( _glfwLibrary.Libs.gdi32 );
_glfwLibrary.Libs.gdi32 = NULL;
}
#endif // _GLFW_NO_DLOAD_GDI32
// winmm.dll
#ifndef _GLFW_NO_DLOAD_WINMM
if( _glfwLibrary.Libs.winmm != NULL )
{
FreeLibrary( _glfwLibrary.Libs.winmm );
_glfwLibrary.Libs.winmm = NULL;
}
#endif // _GLFW_NO_DLOAD_WINMM
}
//========================================================================
// Initialize GLFW thread package
//========================================================================
static void _glfwInitThreads( void )
{
// Initialize critical section handle
InitializeCriticalSection( &_glfwThrd.CriticalSection );
// The first thread (the main thread) has ID 0
_glfwThrd.NextID = 0;
// Fill out information about the main thread (this thread)
_glfwThrd.First.ID = _glfwThrd.NextID ++;
_glfwThrd.First.Function = NULL;
_glfwThrd.First.Handle = GetCurrentThread();
_glfwThrd.First.WinID = GetCurrentThreadId();
_glfwThrd.First.Previous = NULL;
_glfwThrd.First.Next = NULL;
}
//========================================================================
// Terminate GLFW thread package
//========================================================================
static void _glfwTerminateThreads( void )
{
_GLFWthread *t, *t_next;
// Enter critical section
ENTER_THREAD_CRITICAL_SECTION
// Kill all threads (NOTE: THE USER SHOULD WAIT FOR ALL THREADS TO
// DIE, _BEFORE_ CALLING glfwTerminate()!!!)
t = _glfwThrd.First.Next;
while( t != NULL )
{
// Get pointer to next thread
t_next = t->Next;
// Simply murder the process, no mercy!
if( TerminateThread( t->Handle, 0 ) )
{
// Close thread handle
CloseHandle( t->Handle );
// Free memory allocated for this thread
free( (void *) t );
}
// Select next thread in list
t = t_next;
}
// Leave critical section
LEAVE_THREAD_CRITICAL_SECTION
// Delete critical section handle
DeleteCriticalSection( &_glfwThrd.CriticalSection );
}
//========================================================================
// Terminate GLFW when exiting application
//========================================================================
void _glfwTerminate_atexit( void )
{
glfwTerminate();
}
//************************************************************************
//**** Platform implementation functions ****
//************************************************************************
//========================================================================
// Initialize various GLFW state
//========================================================================
int _glfwPlatformInit( void )
{
OSVERSIONINFO osi;
// To make SetForegroundWindow() work as we want, we need to fiddle
// with the FOREGROUNDLOCKTIMEOUT system setting (we do this as early
// as possible in the hope of still being the foreground process)
SystemParametersInfo( SPI_GETFOREGROUNDLOCKTIMEOUT, 0,
&_glfwLibrary.Sys.foregroundLockTimeout, 0 );
SystemParametersInfo( SPI_SETFOREGROUNDLOCKTIMEOUT, 0, (LPVOID)0,
SPIF_SENDCHANGE );
// Check which OS version we are running
osi.dwOSVersionInfoSize = sizeof( OSVERSIONINFO );
// OZZ, temprorary disable warning 4996
#pragma warning(push)
#pragma warning(disable:4996)
GetVersionEx( &osi );
#pragma warning(pop)
_glfwLibrary.Sys.winVer = _GLFW_WIN_UNKNOWN;
if( osi.dwPlatformId == VER_PLATFORM_WIN32_WINDOWS )
{
if( osi.dwMajorVersion == 4 && osi.dwMinorVersion < 10 )
{
_glfwLibrary.Sys.winVer = _GLFW_WIN_95;
}
else if( osi.dwMajorVersion == 4 && osi.dwMinorVersion < 90 )
{
_glfwLibrary.Sys.winVer = _GLFW_WIN_98;
}
else if( osi.dwMajorVersion == 4 && osi.dwMinorVersion == 90 )
{
_glfwLibrary.Sys.winVer = _GLFW_WIN_ME;
}
else if( osi.dwMajorVersion >= 4 )
{
_glfwLibrary.Sys.winVer = _GLFW_WIN_UNKNOWN_9x;
}
}
else if( osi.dwPlatformId == VER_PLATFORM_WIN32_NT )
{
if( osi.dwMajorVersion == 4 && osi.dwMinorVersion == 0 )
{
_glfwLibrary.Sys.winVer = _GLFW_WIN_NT4;
}
else if( osi.dwMajorVersion == 5 && osi.dwMinorVersion == 0 )
{
_glfwLibrary.Sys.winVer = _GLFW_WIN_2K;
}
else if( osi.dwMajorVersion == 5 && osi.dwMinorVersion == 1 )
{
_glfwLibrary.Sys.winVer = _GLFW_WIN_XP;
}
else if( osi.dwMajorVersion == 5 && osi.dwMinorVersion == 2 )
{
_glfwLibrary.Sys.winVer = _GLFW_WIN_NET_SERVER;
}
else if( osi.dwMajorVersion >= 5 )
{
_glfwLibrary.Sys.winVer = _GLFW_WIN_UNKNOWN_NT;
}
}
// Do we have Unicode support?
if( _glfwLibrary.Sys.winVer >= _GLFW_WIN_NT4 )
{
// Windows NT/2000/XP/.NET has Unicode support
_glfwLibrary.Sys.hasUnicode = GL_TRUE;
}
else
{
// Windows 9x/ME does not have Unicode support
_glfwLibrary.Sys.hasUnicode = GL_FALSE;
}
// Load libraries (DLLs)
if( !_glfwInitLibraries() )
{
return GL_FALSE;
}
// With the Borland C++ compiler, we want to disable FPU exceptions
// (this is recommended for OpenGL applications under Windows)
#ifdef __BORLANDC__
_control87( MCW_EM, MCW_EM );
#endif
// Retrieve GLFW instance handle
_glfwLibrary.instance = GetModuleHandle( NULL );
// System keys are not disabled
_glfwWin.keyboardHook = NULL;
// Initialise thread package
_glfwInitThreads();
_glfwPlatformGetDesktopMode( &_glfwLibrary.desktopMode );
// Install atexit() routine
atexit( _glfwTerminate_atexit );
// Start the timer
_glfwInitTimer();
return GL_TRUE;
}
//========================================================================
// Close window and kill all threads
//========================================================================
int _glfwPlatformTerminate( void )
{
// Only the main thread is allowed to do this...
if( GetCurrentThreadId() != _glfwThrd.First.WinID )
{
return GL_FALSE;
}
// Close OpenGL window
glfwCloseWindow();
// Kill thread package
_glfwTerminateThreads();
// Enable system keys again (if they were disabled)
glfwEnable( GLFW_SYSTEM_KEYS );
// Unload libraries (DLLs)
_glfwFreeLibraries();
// Restore FOREGROUNDLOCKTIMEOUT system setting
SystemParametersInfo( SPI_SETFOREGROUNDLOCKTIMEOUT, 0,
(LPVOID) (INT_PTR) _glfwLibrary.Sys.foregroundLockTimeout,
SPIF_SENDCHANGE );
return GL_TRUE;
}
@@ -0,0 +1,233 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Win32/WGL
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
//************************************************************************
//**** GLFW internal functions ****
//************************************************************************
//========================================================================
// Return GL_TRUE if joystick is present, else return GL_FALSE.
//========================================================================
static int _glfwJoystickPresent( int joy )
{
JOYINFO ji;
// Windows NT 4.0 MMSYSTEM only supports 2 sticks (other Windows
// versions support 16 sticks)
if( _glfwLibrary.Sys.winVer == _GLFW_WIN_NT4 && joy > GLFW_JOYSTICK_2 )
{
return GL_FALSE;
}
// Is it a valid stick ID (Windows don't support more than 16 sticks)?
if( joy < GLFW_JOYSTICK_1 || joy > GLFW_JOYSTICK_16 )
{
return GL_FALSE;
}
// Is the joystick present?
if( _glfw_joyGetPos( joy - GLFW_JOYSTICK_1, &ji ) != JOYERR_NOERROR )
{
return GL_FALSE;
}
return GL_TRUE;
}
//========================================================================
// Calculate joystick position
//========================================================================
static float _glfwCalcJoystickPos( DWORD pos, DWORD min, DWORD max )
{
float fpos = (float) pos;
float fmin = (float) min;
float fmax = (float) max;
return (2.0f*(fpos - fmin) / (fmax - fmin)) - 1.0f;
}
//************************************************************************
//**** Platform implementation functions ****
//************************************************************************
//========================================================================
// Determine joystick capabilities
//========================================================================
int _glfwPlatformGetJoystickParam( int joy, int param )
{
JOYCAPS jc;
// return 0;
// Is joystick present?
if( !_glfwJoystickPresent( joy ) )
{
return 0;
}
// We got this far, the joystick is present
if( param == GLFW_PRESENT )
{
return GL_TRUE;
}
// Get joystick capabilities
_glfw_joyGetDevCaps( joy - GLFW_JOYSTICK_1, &jc, sizeof(JOYCAPS) );
switch( param )
{
case GLFW_AXES:
// Return number of joystick axes
return jc.wNumAxes;
case GLFW_BUTTONS:
// Return number of joystick axes
return jc.wNumButtons;
default:
break;
}
return 0;
}
//========================================================================
// Get joystick axis positions
//========================================================================
int _glfwPlatformGetJoystickPos( int joy, float *pos, int numaxes )
{
JOYCAPS jc;
JOYINFOEX ji;
int axis;
// return 0;
// Is joystick present?
if( !_glfwJoystickPresent( joy ) )
{
return 0;
}
// Get joystick capabilities
_glfw_joyGetDevCaps( joy - GLFW_JOYSTICK_1, &jc, sizeof(JOYCAPS) );
// Get joystick state
ji.dwSize = sizeof( JOYINFOEX );
ji.dwFlags = JOY_RETURNX | JOY_RETURNY | JOY_RETURNZ |
JOY_RETURNR | JOY_RETURNU | JOY_RETURNV;
_glfw_joyGetPosEx( joy - GLFW_JOYSTICK_1, &ji );
// Get position values for all axes
axis = 0;
if( axis < numaxes )
{
pos[ axis++ ] = _glfwCalcJoystickPos( ji.dwXpos, jc.wXmin,
jc.wXmax );
}
if( axis < numaxes )
{
pos[ axis++ ] = -_glfwCalcJoystickPos( ji.dwYpos, jc.wYmin,
jc.wYmax );
}
if( axis < numaxes && jc.wCaps & JOYCAPS_HASZ )
{
pos[ axis++ ] = _glfwCalcJoystickPos( ji.dwZpos, jc.wZmin,
jc.wZmax );
}
if( axis < numaxes && jc.wCaps & JOYCAPS_HASR )
{
pos[ axis++ ] = _glfwCalcJoystickPos( ji.dwRpos, jc.wRmin,
jc.wRmax );
}
if( axis < numaxes && jc.wCaps & JOYCAPS_HASU )
{
pos[ axis++ ] = _glfwCalcJoystickPos( ji.dwUpos, jc.wUmin,
jc.wUmax );
}
if( axis < numaxes && jc.wCaps & JOYCAPS_HASV )
{
pos[ axis++ ] = -_glfwCalcJoystickPos( ji.dwVpos, jc.wVmin,
jc.wVmax );
}
// Return number of returned axes
return axis;
}
//========================================================================
// Get joystick button states
//========================================================================
int _glfwPlatformGetJoystickButtons( int joy, unsigned char *buttons,
int numbuttons )
{
JOYCAPS jc;
JOYINFOEX ji;
int button;
// return 0;
// Is joystick present?
if( !_glfwJoystickPresent( joy ) )
{
return 0;
}
// Get joystick capabilities
_glfw_joyGetDevCaps( joy - GLFW_JOYSTICK_1, &jc, sizeof(JOYCAPS) );
// Get joystick state
ji.dwSize = sizeof( JOYINFOEX );
ji.dwFlags = JOY_RETURNBUTTONS;
_glfw_joyGetPosEx( joy - GLFW_JOYSTICK_1, &ji );
// Get states of all requested buttons
button = 0;
while( button < numbuttons && button < (int) jc.wNumButtons )
{
buttons[ button ] = (unsigned char)
(ji.dwButtons & (1UL << button) ? GLFW_PRESS : GLFW_RELEASE);
button ++;
}
return button;
}
@@ -0,0 +1,506 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Win32/WGL
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
//************************************************************************
// This is an implementation of POSIX "compatible" condition variables for
// Win32, as described by Douglas C. Schmidt and Irfan Pyarali:
// http://www.cs.wustl.edu/~schmidt/win32-cv-1.html
//************************************************************************
enum {
_GLFW_COND_SIGNAL = 0,
_GLFW_COND_BROADCAST = 1
};
typedef struct {
// Signal and broadcast event HANDLEs
HANDLE events[ 2 ];
// Count of the number of waiters
unsigned int waiters_count;
// Serialize access to <waiters_count>
CRITICAL_SECTION waiters_count_lock;
} _GLFWcond;
//************************************************************************
//**** GLFW internal functions ****
//************************************************************************
//========================================================================
// This is simply a "wrapper" for calling the user thread function.
//========================================================================
DWORD WINAPI _glfwNewThread( LPVOID lpParam )
{
GLFWthreadfun threadfun;
_GLFWthread *t;
// Get pointer to thread information for current thread
t = _glfwGetThreadPointer( _glfwPlatformGetThreadID() );
if( t == NULL )
{
return 0;
}
// Get user thread function pointer
threadfun = t->Function;
// Call the user thread function
threadfun( (void *) lpParam );
// Remove thread from thread list
ENTER_THREAD_CRITICAL_SECTION
_glfwRemoveThread( t );
LEAVE_THREAD_CRITICAL_SECTION
// When the thread function returns, the thread will die...
return 0;
}
//************************************************************************
//**** GLFW user functions ****
//************************************************************************
//========================================================================
// Create a new thread
//========================================================================
GLFWthread _glfwPlatformCreateThread( GLFWthreadfun fun, void *arg )
{
GLFWthread ID;
_GLFWthread *t, *t_tmp;
HANDLE hThread;
DWORD dwThreadId;
// Enter critical section
ENTER_THREAD_CRITICAL_SECTION
// Create a new thread information memory area
t = (_GLFWthread *) malloc( sizeof(_GLFWthread) );
if( t == NULL )
{
// Leave critical section
LEAVE_THREAD_CRITICAL_SECTION
return -1;
}
// Get a new unique thread id
ID = _glfwThrd.NextID ++;
// Store thread information in the thread list
t->Function = fun;
t->ID = ID;
// Create thread
hThread = CreateThread(
NULL, // Default security attributes
0, // Default stack size (1 MB)
_glfwNewThread, // Thread function (a wrapper function)
(LPVOID)arg, // Argument to thread is the user argument
0, // Default creation flags
&dwThreadId // Returned thread identifier
);
// Did the thread creation fail?
if( hThread == NULL )
{
free( (void *) t );
LEAVE_THREAD_CRITICAL_SECTION
return -1;
}
// Store more thread information in the thread list
t->Handle = hThread;
t->WinID = dwThreadId;
// Append thread to thread list
t_tmp = &_glfwThrd.First;
while( t_tmp->Next != NULL )
{
t_tmp = t_tmp->Next;
}
t_tmp->Next = t;
t->Previous = t_tmp;
t->Next = NULL;
// Leave critical section
LEAVE_THREAD_CRITICAL_SECTION
// Return the GLFW thread ID
return ID;
}
//========================================================================
// Kill a thread. NOTE: THIS IS A VERY DANGEROUS OPERATION, AND SHOULD NOT
// BE USED EXCEPT IN EXTREME SITUATIONS!
//========================================================================
void _glfwPlatformDestroyThread( GLFWthread ID )
{
_GLFWthread *t;
// Enter critical section
ENTER_THREAD_CRITICAL_SECTION
// Get thread information pointer
t = _glfwGetThreadPointer( ID );
if( t == NULL )
{
LEAVE_THREAD_CRITICAL_SECTION
return;
}
// Simply murder the process, no mercy!
if( TerminateThread( t->Handle, 0 ) )
{
// Close thread handle
CloseHandle( t->Handle );
// Remove thread from thread list
_glfwRemoveThread( t );
}
// Leave critical section
LEAVE_THREAD_CRITICAL_SECTION
}
//========================================================================
// Wait for a thread to die
//========================================================================
int _glfwPlatformWaitThread( GLFWthread ID, int waitmode )
{
DWORD result;
HANDLE hThread;
_GLFWthread *t;
// Enter critical section
ENTER_THREAD_CRITICAL_SECTION
// Get thread information pointer
t = _glfwGetThreadPointer( ID );
// Is the thread already dead?
if( t == NULL )
{
LEAVE_THREAD_CRITICAL_SECTION
return GL_TRUE;
}
// Get thread handle
hThread = t->Handle;
// Leave critical section
LEAVE_THREAD_CRITICAL_SECTION
// Wait for thread to die
if( waitmode == GLFW_WAIT )
{
result = WaitForSingleObject( hThread, INFINITE );
}
else if( waitmode == GLFW_NOWAIT )
{
result = WaitForSingleObject( hThread, 0 );
}
else
{
return GL_FALSE;
}
// Did we have a time-out?
if( result == WAIT_TIMEOUT )
{
return GL_FALSE;
}
return GL_TRUE;
}
//========================================================================
// Return the thread ID for the current thread
//========================================================================
GLFWthread _glfwPlatformGetThreadID( void )
{
_GLFWthread *t;
GLFWthread ID = -1;
DWORD WinID;
// Get Windows thread ID
WinID = GetCurrentThreadId();
// Enter critical section (to avoid an inconsistent thread list)
ENTER_THREAD_CRITICAL_SECTION
// Loop through entire list of threads to find the matching Windows
// thread ID
for( t = &_glfwThrd.First; t != NULL; t = t->Next )
{
if( t->WinID == WinID )
{
ID = t->ID;
break;
}
}
// Leave critical section
LEAVE_THREAD_CRITICAL_SECTION
// Return the found GLFW thread identifier
return ID;
}
//========================================================================
// Create a mutual exclusion object
//========================================================================
GLFWmutex _glfwPlatformCreateMutex( void )
{
CRITICAL_SECTION *mutex;
// Allocate memory for mutex
mutex = (CRITICAL_SECTION *) malloc( sizeof(CRITICAL_SECTION) );
if( !mutex )
{
return NULL;
}
// Initialize mutex
InitializeCriticalSection( mutex );
// Cast to GLFWmutex and return
return (GLFWmutex) mutex;
}
//========================================================================
// Destroy a mutual exclusion object
//========================================================================
void _glfwPlatformDestroyMutex( GLFWmutex mutex )
{
// Destroy mutex
DeleteCriticalSection( (CRITICAL_SECTION *) mutex );
free( mutex );
}
//========================================================================
// Request access to a mutex
//========================================================================
void _glfwPlatformLockMutex( GLFWmutex mutex )
{
// Wait for mutex to be released
EnterCriticalSection( (CRITICAL_SECTION *) mutex );
}
//========================================================================
// Release a mutex
//========================================================================
void _glfwPlatformUnlockMutex( GLFWmutex mutex )
{
// Release mutex
LeaveCriticalSection( (CRITICAL_SECTION *) mutex );
}
//========================================================================
// Create a new condition variable object
//========================================================================
GLFWcond _glfwPlatformCreateCond( void )
{
_GLFWcond *cond;
// Allocate memory for condition variable
cond = (_GLFWcond *) malloc( sizeof(_GLFWcond) );
if( !cond )
{
return NULL;
}
// Initialize condition variable
cond->waiters_count = 0;
cond->events[ _GLFW_COND_SIGNAL ] = CreateEvent( NULL, FALSE,
FALSE, NULL );
cond->events[ _GLFW_COND_BROADCAST ] = CreateEvent( NULL, TRUE,
FALSE, NULL );
InitializeCriticalSection( &cond->waiters_count_lock );
// Cast to GLFWcond and return
return (GLFWcond) cond;
}
//========================================================================
// Destroy a condition variable object
//========================================================================
void _glfwPlatformDestroyCond( GLFWcond cond )
{
// Close the condition variable handles
CloseHandle( ((_GLFWcond *)cond)->events[ _GLFW_COND_SIGNAL ] );
CloseHandle( ((_GLFWcond *)cond)->events[ _GLFW_COND_BROADCAST ] );
// Delete critical section
DeleteCriticalSection( &((_GLFWcond *)cond)->waiters_count_lock );
// Free memory for condition variable
free( (void *) cond );
}
//========================================================================
// Wait for a condition to be raised
//========================================================================
void _glfwPlatformWaitCond( GLFWcond cond, GLFWmutex mutex, double timeout )
{
_GLFWcond *cv = (_GLFWcond *) cond;
int result, last_waiter;
DWORD timeout_ms;
// Avoid race conditions
EnterCriticalSection( &cv->waiters_count_lock );
cv->waiters_count ++;
LeaveCriticalSection( &cv->waiters_count_lock );
// It's ok to release the mutex here since Win32 manual-reset events
// maintain state when used with SetEvent()
LeaveCriticalSection( (CRITICAL_SECTION *) mutex );
// Translate timeout into milliseconds
if( timeout >= GLFW_INFINITY )
{
timeout_ms = INFINITE;
}
else
{
timeout_ms = (DWORD) (1000.0 * timeout + 0.5);
if( timeout_ms <= 0 )
{
timeout_ms = 1;
}
}
// Wait for either event to become signaled due to glfwSignalCond or
// glfwBroadcastCond being called
result = WaitForMultipleObjects( 2, cv->events, FALSE, timeout_ms );
// Check if we are the last waiter
EnterCriticalSection( &cv->waiters_count_lock );
cv->waiters_count --;
last_waiter = (result == WAIT_OBJECT_0 + _GLFW_COND_BROADCAST) &&
(cv->waiters_count == 0);
LeaveCriticalSection( &cv->waiters_count_lock );
// Some thread called glfwBroadcastCond
if( last_waiter )
{
// We're the last waiter to be notified or to stop waiting, so
// reset the manual event
ResetEvent( cv->events[ _GLFW_COND_BROADCAST ] );
}
// Reacquire the mutex
EnterCriticalSection( (CRITICAL_SECTION *) mutex );
}
//========================================================================
// Signal a condition to one waiting thread
//========================================================================
void _glfwPlatformSignalCond( GLFWcond cond )
{
_GLFWcond *cv = (_GLFWcond *) cond;
int have_waiters;
// Avoid race conditions
EnterCriticalSection( &cv->waiters_count_lock );
have_waiters = cv->waiters_count > 0;
LeaveCriticalSection( &cv->waiters_count_lock );
if( have_waiters )
{
SetEvent( cv->events[ _GLFW_COND_SIGNAL ] );
}
}
//========================================================================
// Broadcast a condition to all waiting threads
//========================================================================
void _glfwPlatformBroadcastCond( GLFWcond cond )
{
_GLFWcond *cv = (_GLFWcond *) cond;
int have_waiters;
// Avoid race conditions
EnterCriticalSection( &cv->waiters_count_lock );
have_waiters = cv->waiters_count > 0;
LeaveCriticalSection( &cv->waiters_count_lock );
if( have_waiters )
{
SetEvent( cv->events[ _GLFW_COND_BROADCAST ] );
}
}
//========================================================================
// Return the number of processors in the system.
//========================================================================
int _glfwPlatformGetNumberOfProcessors( void )
{
SYSTEM_INFO si;
// Get hardware system information
GetSystemInfo( &si );
return (int) si.dwNumberOfProcessors;
}
@@ -0,0 +1,146 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: Win32/WGL
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
//************************************************************************
//**** GLFW internal functions ****
//************************************************************************
//========================================================================
// Initialise timer
//========================================================================
void _glfwInitTimer( void )
{
__int64 freq;
// Check if we have a performance counter
if( QueryPerformanceFrequency( (LARGE_INTEGER *)&freq ) )
{
// Performance counter is available => use it!
_glfwLibrary.Timer.HasPerformanceCounter = GL_TRUE;
// Counter resolution is 1 / counter frequency
_glfwLibrary.Timer.Resolution = 1.0 / (double)freq;
// Set start time for timer
QueryPerformanceCounter( (LARGE_INTEGER *)&_glfwLibrary.Timer.t0_64 );
}
else
{
// No performace counter available => use the tick counter
_glfwLibrary.Timer.HasPerformanceCounter = GL_FALSE;
// Counter resolution is 1 ms
_glfwLibrary.Timer.Resolution = 0.001;
// Set start time for timer
_glfwLibrary.Timer.t0_32 = _glfw_timeGetTime();
}
}
//************************************************************************
//**** Platform implementation functions ****
//************************************************************************
//========================================================================
// Return timer value in seconds
//========================================================================
double _glfwPlatformGetTime( void )
{
double t;
__int64 t_64;
if( _glfwLibrary.Timer.HasPerformanceCounter )
{
QueryPerformanceCounter( (LARGE_INTEGER *)&t_64 );
t = (double)(t_64 - _glfwLibrary.Timer.t0_64);
}
else
{
t = (double)(_glfw_timeGetTime() - _glfwLibrary.Timer.t0_32);
}
// Calculate the current time in seconds
return t * _glfwLibrary.Timer.Resolution;
}
//========================================================================
// Set timer value in seconds
//========================================================================
void _glfwPlatformSetTime( double t )
{
__int64 t_64;
if( _glfwLibrary.Timer.HasPerformanceCounter )
{
QueryPerformanceCounter( (LARGE_INTEGER *)&t_64 );
_glfwLibrary.Timer.t0_64 = t_64 - (__int64)(t/_glfwLibrary.Timer.Resolution);
}
else
{
_glfwLibrary.Timer.t0_32 = _glfw_timeGetTime() - (int)(t*1000.0);
}
}
//========================================================================
// Put a thread to sleep for a specified amount of time
//========================================================================
void _glfwPlatformSleep( double time )
{
DWORD t;
if( time == 0.0 )
{
t = 0;
}
else if( time < 0.001 )
{
t = 1;
}
else if( time > 2147483647.0 )
{
t = 2147483647;
}
else
{
t = (DWORD)(time*1000.0 + 0.5);
}
Sleep( t );
}
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
+529
View File
@@ -0,0 +1,529 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: X11/GLX
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#ifndef _platform_h_
#define _platform_h_
// This is the X11 version of GLFW
#define _GLFW_X11
// Include files
#include <sys/time.h>
#include <unistd.h>
#include <stdint.h>
#include <signal.h>
#include <X11/Xlib.h>
#include <X11/keysym.h>
#include <X11/Xatom.h>
#include <GL/glx.h>
#include "../../include/GL/glfw.h"
// Do we have pthread support?
#ifdef _GLFW_HAS_PTHREAD
#include <pthread.h>
#include <sched.h>
#endif
// We need declarations for GLX version 1.3 or above even if the server doesn't
// support version 1.3
#ifndef GLX_VERSION_1_3
#error "GLX header version 1.3 or above is required"
#endif
#if defined( _GLFW_HAS_XF86VIDMODE ) && defined( _GLFW_HAS_XRANDR )
#error "Xf86VidMode and RandR extensions cannot both be enabled"
#endif
// With XFree86, we can use the XF86VidMode extension
#if defined( _GLFW_HAS_XF86VIDMODE )
#include <X11/extensions/xf86vmode.h>
#endif
#if defined( _GLFW_HAS_XRANDR )
#include <X11/extensions/Xrandr.h>
#endif
// Do we have support for dlopen/dlsym?
#if defined( _GLFW_HAS_DLOPEN )
#include <dlfcn.h>
#endif
// We support two different ways for getting the number of processors in
// the system: sysconf (POSIX) and sysctl (BSD?)
#if defined( _GLFW_HAS_SYSCONF )
// Use a single constant for querying number of online processors using
// the sysconf function (e.g. SGI defines _SC_NPROC_ONLN instead of
// _SC_NPROCESSORS_ONLN)
#ifndef _SC_NPROCESSORS_ONLN
#ifdef _SC_NPROC_ONLN
#define _SC_NPROCESSORS_ONLN _SC_NPROC_ONLN
#else
#error POSIX constant _SC_NPROCESSORS_ONLN not defined!
#endif
#endif
// Macro for querying the number of processors
#define _glfw_numprocessors(n) n=(int)sysconf(_SC_NPROCESSORS_ONLN)
#elif defined( _GLFW_HAS_SYSCTL )
#include <sys/types.h>
#include <sys/sysctl.h>
// Macro for querying the number of processors
#define _glfw_numprocessors(n) { \
int mib[2], ncpu; \
size_t len = 1; \
mib[0] = CTL_HW; \
mib[1] = HW_NCPU; \
n = 1; \
if( sysctl( mib, 2, &ncpu, &len, NULL, 0 ) != -1 ) \
{ \
if( len > 0 ) \
{ \
n = ncpu; \
} \
} \
}
#else
// If neither sysconf nor sysctl is supported, assume single processor
// system
#define _glfw_numprocessors(n) n=1
#endif
// Pointer length integer
// One day, this will most likely move into glfw.h
typedef intptr_t GLFWintptr;
#ifndef GLX_EXT_swap_control
typedef void (*PFNGLXSWAPINTERVALEXTPROC)(Display*,GLXDrawable,int);
#endif /*GLX_MESA_swap_control*/
#ifndef GLX_MESA_swap_control
typedef int (*PFNGLXSWAPINTERVALMESAPROC)(int);
#endif /*GLX_MESA_swap_control*/
#ifndef GLX_SGI_swap_control
// Function signature for GLX_SGI_swap_control
typedef int ( * PFNGLXSWAPINTERVALSGIPROC) (int interval);
#endif /*GLX_SGI_swap_control*/
#ifndef GLX_SGIX_fbconfig
/* Type definitions for GLX_SGIX_fbconfig */
typedef XID GLXFBConfigIDSGIX;
typedef struct __GLXFBConfigRec *GLXFBConfigSGIX;
/* Function signatures for GLX_SGIX_fbconfig */
typedef int ( * PFNGLXGETFBCONFIGATTRIBSGIXPROC) (Display *dpy, GLXFBConfigSGIX config, int attribute, int *value);
typedef GLXFBConfigSGIX * ( * PFNGLXCHOOSEFBCONFIGSGIXPROC) (Display *dpy, int screen, int *attrib_list, int *nelements);
typedef GLXContext ( * PFNGLXCREATECONTEXTWITHCONFIGSGIXPROC) (Display *dpy, GLXFBConfigSGIX config, int render_type, GLXContext share_list, Bool direct);
typedef XVisualInfo * ( * PFNGLXGETVISUALFROMFBCONFIGSGIXPROC) (Display *dpy, GLXFBConfigSGIX config);
/* Tokens for GLX_SGIX_fbconfig */
#define GLX_WINDOW_BIT_SGIX 0x00000001
#define GLX_PIXMAP_BIT_SGIX 0x00000002
#define GLX_RGBA_BIT_SGIX 0x00000001
#define GLX_COLOR_INDEX_BIT_SGIX 0x00000002
#define GLX_DRAWABLE_TYPE_SGIX 0x8010
#define GLX_RENDER_TYPE_SGIX 0x8011
#define GLX_X_RENDERABLE_SGIX 0x8012
#define GLX_FBCONFIG_ID_SGIX 0x8013
#define GLX_RGBA_TYPE_SGIX 0x8014
#define GLX_COLOR_INDEX_TYPE_SGIX 0x8015
#define GLX_SCREEN_EXT 0x800C
#endif /*GLX_SGIX_fbconfig*/
#ifndef GLX_ARB_create_context
/* Tokens for glXCreateContextAttribsARB attributes */
#define GLX_CONTEXT_MAJOR_VERSION_ARB 0x2091
#define GLX_CONTEXT_MINOR_VERSION_ARB 0x2092
#define GLX_CONTEXT_FLAGS_ARB 0x2094
/* Bits for WGL_CONTEXT_FLAGS_ARB */
#define GLX_CONTEXT_DEBUG_BIT_ARB 0x0001
#define GLX_CONTEXT_FORWARD_COMPATIBLE_BIT_ARB 0x0002
/* Prototype for glXCreateContextAttribs */
typedef GLXContext (*PFNGLXCREATECONTEXTATTRIBSARBPROC)( Display *display, GLXFBConfig config, GLXContext share_context, Bool direct, const int *attrib_list);
#endif /*GLX_ARB_create_context*/
#ifndef GLX_ARB_create_context_profile
/* Tokens for glXCreateContextAttribsARB attributes */
#define GLX_CONTEXT_PROFILE_MASK_ARB 0x9126
/* BIts for GLX_CONTEXT_PROFILE_MASK_ARB */
#define GLX_CONTEXT_CORE_PROFILE_BIT_ARB 0x00000001
#define GLX_CONTEXT_COMPATIBILITY_PROFILE_BIT_ARB 0x00000002
#endif /*GLX_ARB_create_context_profile*/
#ifndef GL_VERSION_3_0
typedef const GLubyte * (APIENTRY *PFNGLGETSTRINGIPROC) (GLenum, GLuint);
#endif /*GL_VERSION_3_0*/
//========================================================================
// Global variables (GLFW internals)
//========================================================================
//------------------------------------------------------------------------
// Window structure
//------------------------------------------------------------------------
typedef struct _GLFWwin_struct _GLFWwin;
struct _GLFWwin_struct {
// ========= PLATFORM INDEPENDENT MANDATORY PART =========================
// User callback functions
GLFWwindowsizefun windowSizeCallback;
GLFWwindowclosefun windowCloseCallback;
GLFWwindowrefreshfun windowRefreshCallback;
GLFWmousebuttonfun mouseButtonCallback;
GLFWmouseposfun mousePosCallback;
GLFWmousewheelfun mouseWheelCallback;
GLFWkeyfun keyCallback;
GLFWcharfun charCallback;
// User selected window settings
int fullscreen; // Fullscreen flag
int mouseLock; // Mouse-lock flag
int autoPollEvents; // Auto polling flag
int sysKeysDisabled; // System keys disabled flag
int windowNoResize; // Resize- and maximize gadgets disabled flag
int refreshRate; // Vertical monitor refresh rate
// Window status & parameters
int opened; // Flag telling if window is opened or not
int active; // Application active flag
int iconified; // Window iconified flag
int width, height; // Window width and heigth
int accelerated; // GL_TRUE if window is HW accelerated
// Framebuffer attributes
int redBits;
int greenBits;
int blueBits;
int alphaBits;
int depthBits;
int stencilBits;
int accumRedBits;
int accumGreenBits;
int accumBlueBits;
int accumAlphaBits;
int auxBuffers;
int stereo;
int samples;
// OpenGL extensions and context attributes
int has_GL_SGIS_generate_mipmap;
int has_GL_ARB_texture_non_power_of_two;
int glMajor, glMinor, glRevision;
int glForward, glDebug, glProfile;
PFNGLGETSTRINGIPROC GetStringi;
// ========= PLATFORM SPECIFIC PART ======================================
// Platform specific window resources
Colormap colormap; // Window colormap
Window window; // Window
Window root; // Root window for screen
int screen; // Screen ID
XVisualInfo *visual; // Visual for selected GLXFBConfig
GLXFBConfigID fbconfigID; // ID of selected GLXFBConfig
GLXContext context; // OpenGL rendering context
Atom wmDeleteWindow; // WM_DELETE_WINDOW atom
Atom wmPing; // _NET_WM_PING atom
Atom wmState; // _NET_WM_STATE atom
Atom wmStateFullscreen; // _NET_WM_STATE_FULLSCREEN atom
Atom wmActiveWindow; // _NET_ACTIVE_WINDOW atom
Cursor cursor; // Invisible cursor for hidden cursor
// GLX extensions
PFNGLXSWAPINTERVALEXTPROC SwapIntervalEXT;
PFNGLXSWAPINTERVALMESAPROC SwapIntervalMESA;
PFNGLXSWAPINTERVALSGIPROC SwapIntervalSGI;
PFNGLXGETFBCONFIGATTRIBSGIXPROC GetFBConfigAttribSGIX;
PFNGLXCHOOSEFBCONFIGSGIXPROC ChooseFBConfigSGIX;
PFNGLXCREATECONTEXTWITHCONFIGSGIXPROC CreateContextWithConfigSGIX;
PFNGLXGETVISUALFROMFBCONFIGSGIXPROC GetVisualFromFBConfigSGIX;
PFNGLXCREATECONTEXTATTRIBSARBPROC CreateContextAttribsARB;
GLboolean has_GLX_SGIX_fbconfig;
GLboolean has_GLX_EXT_swap_control;
GLboolean has_GLX_MESA_swap_control;
GLboolean has_GLX_SGI_swap_control;
GLboolean has_GLX_ARB_multisample;
GLboolean has_GLX_ARB_create_context;
GLboolean has_GLX_ARB_create_context_profile;
// Various platform specific internal variables
GLboolean hasEWMH; // True if window manager supports EWMH
GLboolean overrideRedirect; // True if window is OverrideRedirect
GLboolean keyboardGrabbed; // True if keyboard is currently grabbed
GLboolean pointerGrabbed; // True if pointer is currently grabbed
GLboolean pointerHidden; // True if pointer is currently hidden
// Screensaver data
struct {
int changed;
int timeout;
int interval;
int blanking;
int exposure;
} Saver;
// Fullscreen data
struct {
int modeChanged;
#if defined( _GLFW_HAS_XF86VIDMODE )
XF86VidModeModeInfo oldMode;
#endif
#if defined( _GLFW_HAS_XRANDR )
SizeID oldSizeID;
int oldWidth;
int oldHeight;
Rotation oldRotation;
#endif
} FS;
};
GLFWGLOBAL _GLFWwin _glfwWin;
//------------------------------------------------------------------------
// User input status (most of this should go in _GLFWwin)
//------------------------------------------------------------------------
GLFWGLOBAL struct {
// ========= PLATFORM INDEPENDENT MANDATORY PART =========================
// Mouse status
int MousePosX, MousePosY;
int WheelPos;
char MouseButton[ GLFW_MOUSE_BUTTON_LAST+1 ];
// Keyboard status
char Key[ GLFW_KEY_LAST+1 ];
int LastChar;
// User selected settings
int StickyKeys;
int StickyMouseButtons;
int KeyRepeat;
// ========= PLATFORM SPECIFIC PART ======================================
// Platform specific internal variables
int MouseMoved, CursorPosX, CursorPosY;
} _glfwInput;
//------------------------------------------------------------------------
// Library global data
//------------------------------------------------------------------------
GLFWGLOBAL struct {
// ========= PLATFORM INDEPENDENT MANDATORY PART =========================
// Window opening hints
_GLFWhints hints;
// Initial desktop mode
GLFWvidmode desktopMode;
// ========= PLATFORM SPECIFIC PART ======================================
Display *display;
struct {
int versionMajor, versionMinor;
int eventBase;
int errorBase;
} GLX;
struct {
int available;
int eventBase;
int errorBase;
} XF86VidMode;
struct {
int available;
int eventBase;
int errorBase;
} XRandR;
// Timer data
struct {
GLboolean monotonic;
double resolution;
long long base;
} Timer;
#if defined(_GLFW_HAS_DLOPEN)
struct {
void *libGL; // dlopen handle for libGL.so
} Libs;
#endif
} _glfwLibrary;
//------------------------------------------------------------------------
// Thread record (one for each thread)
//------------------------------------------------------------------------
typedef struct _GLFWthread_struct _GLFWthread;
struct _GLFWthread_struct {
// ========= PLATFORM INDEPENDENT MANDATORY PART =========================
// Pointer to previous and next threads in linked list
_GLFWthread *Previous, *Next;
// GLFW user side thread information
GLFWthread ID;
GLFWthreadfun Function;
// ========= PLATFORM SPECIFIC PART ======================================
// System side thread information
#ifdef _GLFW_HAS_PTHREAD
pthread_t PosixID;
#endif
};
//------------------------------------------------------------------------
// General thread information
//------------------------------------------------------------------------
GLFWGLOBAL struct {
// ========= PLATFORM INDEPENDENT MANDATORY PART =========================
// Next thread ID to use (increments for every created thread)
GLFWthread NextID;
// First thread in linked list (always the main thread)
_GLFWthread First;
// ========= PLATFORM SPECIFIC PART ======================================
// Critical section lock
#ifdef _GLFW_HAS_PTHREAD
pthread_mutex_t CriticalSection;
#endif
} _glfwThrd;
//------------------------------------------------------------------------
// Joystick information & state
//------------------------------------------------------------------------
GLFWGLOBAL struct {
int Present;
int fd;
int NumAxes;
int NumButtons;
float *Axis;
unsigned char *Button;
} _glfwJoy[ GLFW_JOYSTICK_LAST + 1 ];
//========================================================================
// Macros for encapsulating critical code sections (i.e. making parts
// of GLFW thread safe)
//========================================================================
// Thread list management
#ifdef _GLFW_HAS_PTHREAD
#define ENTER_THREAD_CRITICAL_SECTION \
pthread_mutex_lock( &_glfwThrd.CriticalSection );
#define LEAVE_THREAD_CRITICAL_SECTION \
pthread_mutex_unlock( &_glfwThrd.CriticalSection );
#else
#define ENTER_THREAD_CRITICAL_SECTION
#define LEAVE_THREAD_CRITICAL_SECTION
#endif
//========================================================================
// Prototypes for platform specific internal functions
//========================================================================
// Time
void _glfwInitTimer( void );
// Fullscreen support
int _glfwGetClosestVideoMode( int screen, int *width, int *height, int *rate );
void _glfwSetVideoModeMODE( int screen, int mode, int rate );
void _glfwSetVideoMode( int screen, int *width, int *height, int *rate );
void _glfwRestoreVideoMode( void );
// Joystick input
void _glfwInitJoysticks( void );
void _glfwTerminateJoysticks( void );
// Unicode support
long _glfwKeySym2Unicode( KeySym keysym );
#endif // _platform_h_
+64
View File
@@ -0,0 +1,64 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: X11 (Unix)
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
//************************************************************************
//**** Platform implementation functions ****
//************************************************************************
//========================================================================
// Enable system keys
//========================================================================
void _glfwPlatformEnableSystemKeys( void )
{
if( _glfwWin.keyboardGrabbed )
{
XUngrabKeyboard( _glfwLibrary.display, CurrentTime );
_glfwWin.keyboardGrabbed = GL_FALSE;
}
}
//========================================================================
// Disable system keys
//========================================================================
void _glfwPlatformDisableSystemKeys( void )
{
if( XGrabKeyboard( _glfwLibrary.display, _glfwWin.window, True,
GrabModeAsync, GrabModeAsync, CurrentTime ) ==
GrabSuccess )
{
_glfwWin.keyboardGrabbed = GL_TRUE;
}
}
@@ -0,0 +1,567 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: X11/GLX
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
#include <limits.h>
//************************************************************************
//**** GLFW internal functions ****
//************************************************************************
//========================================================================
// Convert BPP to RGB bits (based on "best guess")
//========================================================================
static void BPP2RGB( int bpp, int *r, int *g, int *b )
{
int delta;
// Special case: BPP = 32 (I don't think this is necessary for X11??)
if( bpp == 32 )
bpp = 24;
// Convert "bits per pixel" to red, green & blue sizes
*r = *g = *b = bpp / 3;
delta = bpp - (*r * 3);
if( delta >= 1 )
{
*g = *g + 1;
}
if( delta == 2 )
{
*r = *r + 1;
}
}
//========================================================================
// Finds the video mode closest in size to the specified desired size
//========================================================================
int _glfwGetClosestVideoMode( int screen, int *width, int *height, int *rate )
{
#if defined( _GLFW_HAS_XRANDR )
int i, match, bestmatch;
int sizecount, bestsize;
int ratecount, bestrate;
short *ratelist;
XRRScreenConfiguration *sc;
XRRScreenSize *sizelist;
if( _glfwLibrary.XRandR.available )
{
sc = XRRGetScreenInfo( _glfwLibrary.display,
RootWindow( _glfwLibrary.display, screen ) );
sizelist = XRRConfigSizes( sc, &sizecount );
// Find the best matching mode
bestsize = -1;
bestmatch = INT_MAX;
for( i = 0; i < sizecount; i++ )
{
match = (*width - sizelist[i].width) *
(*width - sizelist[i].width) +
(*height - sizelist[i].height) *
(*height - sizelist[i].height);
if( match < bestmatch )
{
bestmatch = match;
bestsize = i;
}
}
if( bestsize != -1 )
{
// Report width & height of best matching mode
*width = sizelist[bestsize].width;
*height = sizelist[bestsize].height;
if( *rate > 0 )
{
ratelist = XRRConfigRates( sc, bestsize, &ratecount );
bestrate = -1;
bestmatch = INT_MAX;
for( i = 0; i < ratecount; i++ )
{
match = abs( ratelist[i] - *rate );
if( match < bestmatch )
{
bestmatch = match;
bestrate = ratelist[i];
}
}
if( bestrate != -1 )
{
*rate = bestrate;
}
}
}
// Free modelist
XRRFreeScreenConfigInfo( sc );
if( bestsize != -1 )
{
return bestsize;
}
}
#elif defined( _GLFW_HAS_XF86VIDMODE )
XF86VidModeModeInfo **modelist;
int modecount, i, bestmode, bestmatch, match;
// Use the XF86VidMode extension to control video resolution
if( _glfwLibrary.XF86VidMode.available )
{
// Get a list of all available display modes
XF86VidModeGetAllModeLines( _glfwLibrary.display, screen,
&modecount, &modelist );
// Find the best matching mode
bestmode = -1;
bestmatch = INT_MAX;
for( i = 0; i < modecount; i++ )
{
match = (*width - modelist[i]->hdisplay) *
(*width - modelist[i]->hdisplay) +
(*height - modelist[i]->vdisplay) *
(*height - modelist[i]->vdisplay);
if( match < bestmatch )
{
bestmatch = match;
bestmode = i;
}
}
if( bestmode != -1 )
{
// Report width & height of best matching mode
*width = modelist[ bestmode ]->hdisplay;
*height = modelist[ bestmode ]->vdisplay;
}
// Free modelist
XFree( modelist );
if( bestmode != -1 )
{
return bestmode;
}
}
#endif
// Default: Simply use the screen resolution
*width = DisplayWidth( _glfwLibrary.display, screen );
*height = DisplayHeight( _glfwLibrary.display, screen );
return 0;
}
//========================================================================
// Change the current video mode
//========================================================================
void _glfwSetVideoModeMODE( int screen, int mode, int rate )
{
#if defined( _GLFW_HAS_XRANDR )
XRRScreenConfiguration *sc;
Window root;
if( _glfwLibrary.XRandR.available )
{
root = RootWindow( _glfwLibrary.display, screen );
sc = XRRGetScreenInfo( _glfwLibrary.display, root );
// Remember old size and flag that we have changed the mode
if( !_glfwWin.FS.modeChanged )
{
_glfwWin.FS.oldSizeID = XRRConfigCurrentConfiguration( sc, &_glfwWin.FS.oldRotation );
_glfwWin.FS.oldWidth = DisplayWidth( _glfwLibrary.display, screen );
_glfwWin.FS.oldHeight = DisplayHeight( _glfwLibrary.display, screen );
_glfwWin.FS.modeChanged = GL_TRUE;
}
if( rate > 0 )
{
// Set desired configuration
XRRSetScreenConfigAndRate( _glfwLibrary.display,
sc,
root,
mode,
RR_Rotate_0,
(short) rate,
CurrentTime );
}
else
{
// Set desired configuration
XRRSetScreenConfig( _glfwLibrary.display,
sc,
root,
mode,
RR_Rotate_0,
CurrentTime );
}
XRRFreeScreenConfigInfo( sc );
}
#elif defined( _GLFW_HAS_XF86VIDMODE )
XF86VidModeModeInfo **modelist;
int modecount;
// Use the XF86VidMode extension to control video resolution
if( _glfwLibrary.XF86VidMode.available )
{
// Get a list of all available display modes
XF86VidModeGetAllModeLines( _glfwLibrary.display, screen,
&modecount, &modelist );
// Unlock mode switch if necessary
if( _glfwWin.FS.modeChanged )
{
XF86VidModeLockModeSwitch( _glfwLibrary.display, screen, 0 );
}
// Change the video mode to the desired mode
XF86VidModeSwitchToMode( _glfwLibrary.display, screen,
modelist[ mode ] );
// Set viewport to upper left corner (where our window will be)
XF86VidModeSetViewPort( _glfwLibrary.display, screen, 0, 0 );
// Lock mode switch
XF86VidModeLockModeSwitch( _glfwLibrary.display, screen, 1 );
// Remember old mode and flag that we have changed the mode
if( !_glfwWin.FS.modeChanged )
{
_glfwWin.FS.oldMode = *modelist[ 0 ];
_glfwWin.FS.modeChanged = GL_TRUE;
}
// Free mode list
XFree( modelist );
}
#endif
}
//========================================================================
// Change the current video mode
//========================================================================
void _glfwSetVideoMode( int screen, int *width, int *height, int *rate )
{
int bestmode;
// Find a best match mode
bestmode = _glfwGetClosestVideoMode( screen, width, height, rate );
// Change mode
_glfwSetVideoModeMODE( screen, bestmode, *rate );
}
//========================================================================
// Restore the previously saved (original) video mode
//========================================================================
void _glfwRestoreVideoMode( void )
{
if( _glfwWin.FS.modeChanged )
{
#if defined( _GLFW_HAS_XRANDR )
if( _glfwLibrary.XRandR.available )
{
XRRScreenConfiguration *sc;
sc = XRRGetScreenInfo( _glfwLibrary.display, _glfwWin.root );
XRRSetScreenConfig( _glfwLibrary.display,
sc,
_glfwWin.root,
_glfwWin.FS.oldSizeID,
_glfwWin.FS.oldRotation,
CurrentTime );
XRRFreeScreenConfigInfo( sc );
}
#elif defined( _GLFW_HAS_XF86VIDMODE )
if( _glfwLibrary.XF86VidMode.available )
{
// Unlock mode switch
XF86VidModeLockModeSwitch( _glfwLibrary.display, _glfwWin.screen, 0 );
// Change the video mode back to the old mode
XF86VidModeSwitchToMode( _glfwLibrary.display,
_glfwWin.screen,
&_glfwWin.FS.oldMode );
}
#endif
_glfwWin.FS.modeChanged = GL_FALSE;
}
}
//************************************************************************
//**** Platform implementation functions ****
//************************************************************************
struct _glfwResolution
{
int width;
int height;
};
//========================================================================
// List available video modes
//========================================================================
int _glfwPlatformGetVideoModes( GLFWvidmode *list, int maxcount )
{
int count, k, l, r, g, b, rgba, gl;
int depth, screen;
Display *dpy;
XVisualInfo *vislist, dummy;
int viscount, rgbcount, rescount;
int *rgbarray;
struct _glfwResolution *resarray;
// Get display and screen
dpy = _glfwLibrary.display;
screen = DefaultScreen( dpy );
// Get list of visuals
vislist = XGetVisualInfo( dpy, 0, &dummy, &viscount );
if( vislist == NULL )
{
return 0;
}
rgbarray = (int*) malloc( sizeof(int) * viscount );
rgbcount = 0;
// Build RGB array
for( k = 0; k < viscount; k++ )
{
// Does the visual support OpenGL & true color?
glXGetConfig( dpy, &vislist[k], GLX_USE_GL, &gl );
glXGetConfig( dpy, &vislist[k], GLX_RGBA, &rgba );
if( gl && rgba )
{
// Get color depth for this visual
depth = vislist[k].depth;
// Convert to RGB
BPP2RGB( depth, &r, &g, &b );
depth = (r<<16) | (g<<8) | b;
// Is this mode unique?
for( l = 0; l < rgbcount; l++ )
{
if( depth == rgbarray[ l ] )
{
break;
}
}
if( l >= rgbcount )
{
rgbarray[ rgbcount ] = depth;
rgbcount++;
}
}
}
rescount = 0;
resarray = NULL;
// Build resolution array
#if defined( _GLFW_HAS_XRANDR )
if( _glfwLibrary.XRandR.available )
{
XRRScreenConfiguration *sc;
XRRScreenSize *sizelist;
int sizecount;
sc = XRRGetScreenInfo( dpy, RootWindow( dpy, screen ) );
sizelist = XRRConfigSizes( sc, &sizecount );
resarray = (struct _glfwResolution*) malloc( sizeof(struct _glfwResolution) * sizecount );
for( k = 0; k < sizecount; k++ )
{
resarray[ rescount ].width = sizelist[ k ].width;
resarray[ rescount ].height = sizelist[ k ].height;
rescount++;
}
XRRFreeScreenConfigInfo( sc );
}
#elif defined( _GLFW_HAS_XF86VIDMODE )
if( _glfwLibrary.XF86VidMode.available )
{
XF86VidModeModeInfo **modelist;
int modecount, width, height;
XF86VidModeGetAllModeLines( dpy, screen, &modecount, &modelist );
resarray = (struct _glfwResolution*) malloc( sizeof(struct _glfwResolution) * modecount );
for( k = 0; k < modecount; k++ )
{
width = modelist[ k ]->hdisplay;
height = modelist[ k ]->vdisplay;
// Is this mode unique?
for( l = 0; l < rescount; l++ )
{
if( width == resarray[ l ].width && height == resarray[ l ].height )
{
break;
}
}
if( l >= rescount )
{
resarray[ rescount ].width = width;
resarray[ rescount ].height = height;
rescount++;
}
}
XFree( modelist );
}
#endif
if( !resarray )
{
rescount = 1;
resarray = (struct _glfwResolution*) malloc( sizeof(struct _glfwResolution) * rescount );
resarray[ 0 ].width = DisplayWidth( dpy, screen );
resarray[ 0 ].height = DisplayHeight( dpy, screen );
}
// Build permutations of colors and resolutions
count = 0;
for( k = 0; k < rgbcount && count < maxcount; k++ )
{
for( l = 0; l < rescount && count < maxcount; l++ )
{
list[count].Width = resarray[ l ].width;
list[count].Height = resarray[ l ].height;
list[count].RedBits = (rgbarray[ k ] >> 16) & 255;
list[count].GreenBits = (rgbarray[ k ] >> 8) & 255;
list[count].BlueBits = rgbarray[ k ] & 255;
count++;
}
}
// Free visuals list
XFree( vislist );
free( resarray );
free( rgbarray );
return count;
}
//========================================================================
// Get the desktop video mode
//========================================================================
void _glfwPlatformGetDesktopMode( GLFWvidmode *mode )
{
Display *dpy;
int bpp, screen;
// Get display and screen
dpy = _glfwLibrary.display;
screen = DefaultScreen( dpy );
// Get display depth
bpp = DefaultDepth( dpy, screen );
// Convert BPP to RGB bits
BPP2RGB( bpp, &mode->RedBits, &mode->GreenBits, &mode->BlueBits );
#if defined( _GLFW_HAS_XRANDR )
if( _glfwLibrary.XRandR.available )
{
if( _glfwWin.FS.modeChanged )
{
mode->Width = _glfwWin.FS.oldWidth;
mode->Height = _glfwWin.FS.oldHeight;
return;
}
}
#elif defined( _GLFW_HAS_XF86VIDMODE )
if( _glfwLibrary.XF86VidMode.available )
{
XF86VidModeModeInfo **modelist;
int modecount;
if( _glfwWin.FS.modeChanged )
{
// The old (desktop) mode is stored in _glfwWin.FS.oldMode
mode->Width = _glfwWin.FS.oldMode.hdisplay;
mode->Height = _glfwWin.FS.oldMode.vdisplay;
}
else
{
// Use the XF86VidMode extension to get list of video modes
XF86VidModeGetAllModeLines( dpy, screen, &modecount,
&modelist );
// The first mode in the list is the current (desktio) mode
mode->Width = modelist[ 0 ]->hdisplay;
mode->Height = modelist[ 0 ]->vdisplay;
// Free list
XFree( modelist );
}
return;
}
#endif
// Get current display width and height
mode->Width = DisplayWidth( dpy, screen );
mode->Height = DisplayHeight( dpy, screen );
}
+89
View File
@@ -0,0 +1,89 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: X11/GLX
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
void (*glXGetProcAddress(const GLubyte *procName))();
void (*glXGetProcAddressARB(const GLubyte *procName))();
void (*glXGetProcAddressEXT(const GLubyte *procName))();
// We support four different ways for getting addresses for GL/GLX
// extension functions: glXGetProcAddress, glXGetProcAddressARB,
// glXGetProcAddressEXT, and dlsym
#if defined( _GLFW_HAS_GLXGETPROCADDRESSARB )
#define _glfw_glXGetProcAddress(x) glXGetProcAddressARB(x)
#elif defined( _GLFW_HAS_GLXGETPROCADDRESS )
#define _glfw_glXGetProcAddress(x) glXGetProcAddress(x)
#elif defined( _GLFW_HAS_GLXGETPROCADDRESSEXT )
#define _glfw_glXGetProcAddress(x) glXGetProcAddressEXT(x)
#elif defined( _GLFW_HAS_DLOPEN )
#define _glfw_glXGetProcAddress(x) dlsym(_glfwLibrary.Libs.libGL,x)
#else
#define _glfw_glXGetProcAddress(x) NULL
#endif
//************************************************************************
//**** Platform implementation functions ****
//************************************************************************
//========================================================================
// Check if an OpenGL extension is available at runtime
//========================================================================
int _glfwPlatformExtensionSupported( const char *extension )
{
const GLubyte *extensions;
// Get list of GLX extensions
extensions = (const GLubyte*) glXQueryExtensionsString( _glfwLibrary.display,
_glfwWin.screen );
if( extensions != NULL )
{
if( _glfwStringInExtensionString( extension, extensions ) )
{
return GL_TRUE;
}
}
return GL_FALSE;
}
//========================================================================
// Get the function pointer to an OpenGL function
//========================================================================
void * _glfwPlatformGetProcAddress( const char *procname )
{
return (void *) _glfw_glXGetProcAddress( (const GLubyte *) procname );
}
+290
View File
@@ -0,0 +1,290 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: X11/GLX
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
//************************************************************************
//**** GLFW internal functions ****
//************************************************************************
//========================================================================
// Initialize GLFW thread package
//========================================================================
static void initThreads( void )
{
// Initialize critical section handle
#ifdef _GLFW_HAS_PTHREAD
(void) pthread_mutex_init( &_glfwThrd.CriticalSection, NULL );
#endif
// The first thread (the main thread) has ID 0
_glfwThrd.NextID = 0;
// Fill out information about the main thread (this thread)
_glfwThrd.First.ID = _glfwThrd.NextID++;
_glfwThrd.First.Function = NULL;
_glfwThrd.First.Previous = NULL;
_glfwThrd.First.Next = NULL;
#ifdef _GLFW_HAS_PTHREAD
_glfwThrd.First.PosixID = pthread_self();
#endif
}
//========================================================================
// Terminate GLFW thread package
//========================================================================
static void terminateThreads( void )
{
#ifdef _GLFW_HAS_PTHREAD
_GLFWthread *t, *t_next;
// Enter critical section
ENTER_THREAD_CRITICAL_SECTION
// Kill all threads (NOTE: THE USER SHOULD WAIT FOR ALL THREADS TO
// DIE, _BEFORE_ CALLING glfwTerminate()!!!)
t = _glfwThrd.First.Next;
while( t != NULL )
{
// Get pointer to next thread
t_next = t->Next;
// Simply murder the process, no mercy!
pthread_kill( t->PosixID, SIGKILL );
// Free memory allocated for this thread
free( (void *) t );
// Select next thread in list
t = t_next;
}
// Leave critical section
LEAVE_THREAD_CRITICAL_SECTION
// Delete critical section handle
pthread_mutex_destroy( &_glfwThrd.CriticalSection );
#endif // _GLFW_HAS_PTHREAD
}
//========================================================================
// Dynamically load libraries
//========================================================================
static void initLibraries( void )
{
#ifdef _GLFW_DLOPEN_LIBGL
int i;
char *libGL_names[ ] =
{
"libGL.so",
"libGL.so.1",
"/usr/lib/libGL.so",
"/usr/lib/libGL.so.1",
NULL
};
_glfwLibrary.Libs.libGL = NULL;
for( i = 0; !libGL_names[ i ] != NULL; i ++ )
{
_glfwLibrary.Libs.libGL = dlopen( libGL_names[ i ],
RTLD_LAZY | RTLD_GLOBAL );
if( _glfwLibrary.Libs.libGL )
break;
}
#endif
}
//========================================================================
// Terminate GLFW when exiting application
//========================================================================
static void glfw_atexit( void )
{
glfwTerminate();
}
//========================================================================
// Initialize X11 display
//========================================================================
static int initDisplay( void )
{
// Open display
_glfwLibrary.display = XOpenDisplay( 0 );
if( !_glfwLibrary.display )
{
fprintf(stderr, "Failed to open X display\n");
return GL_FALSE;
}
// Check for XF86VidMode extension
#ifdef _GLFW_HAS_XF86VIDMODE
_glfwLibrary.XF86VidMode.available =
XF86VidModeQueryExtension( _glfwLibrary.display,
&_glfwLibrary.XF86VidMode.eventBase,
&_glfwLibrary.XF86VidMode.errorBase);
#else
_glfwLibrary.XF86VidMode.available = 0;
#endif
// Check for XRandR extension
#ifdef _GLFW_HAS_XRANDR
_glfwLibrary.XRandR.available =
XRRQueryExtension( _glfwLibrary.display,
&_glfwLibrary.XRandR.eventBase,
&_glfwLibrary.XRandR.errorBase );
#else
_glfwLibrary.XRandR.available = 0;
#endif
// Fullscreen & screen saver settings
// Check if GLX is supported on this display
if( !glXQueryExtension( _glfwLibrary.display,
&_glfwLibrary.GLX.errorBase,
&_glfwLibrary.GLX.eventBase))
{
fprintf(stderr, "GLX not supported\n");
return GL_FALSE;
}
// Retrieve GLX version
if( !glXQueryVersion( _glfwLibrary.display,
&_glfwLibrary.GLX.versionMajor,
&_glfwLibrary.GLX.versionMinor ) )
{
fprintf(stderr, "Unable to query GLX version\n");
return GL_FALSE;
}
return GL_TRUE;
}
//========================================================================
// Terminate X11 display
//========================================================================
static void terminateDisplay( void )
{
// Open display
if( _glfwLibrary.display )
{
XCloseDisplay( _glfwLibrary.display );
_glfwLibrary.display = NULL;
}
}
//************************************************************************
//**** Platform implementation functions ****
//************************************************************************
//========================================================================
// Initialize various GLFW state
//========================================================================
int _glfwPlatformInit( void )
{
// Initialize display
if( !initDisplay() )
{
return GL_FALSE;
}
// Initialize thread package
initThreads();
// Try to load libGL.so if necessary
initLibraries();
_glfwPlatformGetDesktopMode( &_glfwLibrary.desktopMode );
// Install atexit() routine
atexit( glfw_atexit );
// Initialize joysticks
_glfwInitJoysticks();
// Start the timer
_glfwInitTimer();
return GL_TRUE;
}
//========================================================================
// Close window and kill all threads
//========================================================================
int _glfwPlatformTerminate( void )
{
#ifdef _GLFW_HAS_PTHREAD
// Only the main thread is allowed to do this...
if( pthread_self() != _glfwThrd.First.PosixID )
{
return GL_FALSE;
}
#endif // _GLFW_HAS_PTHREAD
// Close OpenGL window
glfwCloseWindow();
// Kill thread package
terminateThreads();
// Terminate display
terminateDisplay();
// Terminate joysticks
_glfwTerminateJoysticks();
// Unload libGL.so if necessary
#ifdef _GLFW_DLOPEN_LIBGL
if( _glfwLibrary.Libs.libGL != NULL )
{
dlclose( _glfwLibrary.Libs.libGL );
_glfwLibrary.Libs.libGL = NULL;
}
#endif
return GL_TRUE;
}
@@ -0,0 +1,367 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: X11/GLX
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
//========================================================================
// Note: Only Linux joystick input is supported at the moment. Other
// systems will behave as if there are no joysticks connected.
//========================================================================
//************************************************************************
//**** GLFW internal functions ****
//************************************************************************
#ifdef _GLFW_USE_LINUX_JOYSTICKS
//------------------------------------------------------------------------
// Here are the Linux joystick driver v1.x interface definitions that we
// use (we do not want to rely on <linux/joystick.h>):
//------------------------------------------------------------------------
#include <sys/ioctl.h>
#include <fcntl.h>
#include <errno.h>
// Joystick event types
#define JS_EVENT_BUTTON 0x01 /* button pressed/released */
#define JS_EVENT_AXIS 0x02 /* joystick moved */
#define JS_EVENT_INIT 0x80 /* initial state of device */
// Joystick event structure
struct js_event {
unsigned int time; /* (u32) event timestamp in milliseconds */
signed short value; /* (s16) value */
unsigned char type; /* (u8) event type */
unsigned char number; /* (u8) axis/button number */
};
// Joystick IOCTL commands
#define JSIOCGVERSION _IOR('j', 0x01, int) /* get driver version (u32) */
#define JSIOCGAXES _IOR('j', 0x11, char) /* get number of axes (u8) */
#define JSIOCGBUTTONS _IOR('j', 0x12, char) /* get number of buttons (u8) */
#endif // _GLFW_USE_LINUX_JOYSTICKS
//========================================================================
// Initialize joystick interface
//========================================================================
void _glfwInitJoysticks( void )
{
#ifdef _GLFW_USE_LINUX_JOYSTICKS
int k, n, fd, joy_count;
char *joy_base_name, joy_dev_name[ 20 ];
int driver_version = 0x000800;
char ret_data;
#endif // _GLFW_USE_LINUX_JOYSTICKS
int i;
// Start by saying that there are no sticks
for( i = 0; i <= GLFW_JOYSTICK_LAST; ++ i )
{
_glfwJoy[ i ].Present = GL_FALSE;
}
#ifdef _GLFW_USE_LINUX_JOYSTICKS
// Try to open joysticks (nonblocking)
joy_count = 0;
for( k = 0; k <= 1 && joy_count <= GLFW_JOYSTICK_LAST; ++ k )
{
// Pick joystick base name
switch( k )
{
case 0:
joy_base_name = "/dev/input/js"; // USB sticks
break;
case 1:
joy_base_name = "/dev/js"; // "Legacy" sticks
break;
default:
continue; // (should never happen)
}
// Try to open a few of these sticks
for( i = 0; i <= 50 && joy_count <= GLFW_JOYSTICK_LAST; ++ i )
{
sprintf( joy_dev_name, "%s%d", joy_base_name, i );
fd = open( joy_dev_name, O_NONBLOCK );
if( fd != -1 )
{
// Remember fd
_glfwJoy[ joy_count ].fd = fd;
// Check that the joystick driver version is 1.0+
ioctl( fd, JSIOCGVERSION, &driver_version );
if( driver_version < 0x010000 )
{
// It's an old 0.x interface (we don't support it)
close( fd );
continue;
}
// Get number of joystick axes
ioctl( fd, JSIOCGAXES, &ret_data );
_glfwJoy[ joy_count ].NumAxes = (int) ret_data;
// Get number of joystick buttons
ioctl( fd, JSIOCGBUTTONS, &ret_data );
_glfwJoy[ joy_count ].NumButtons = (int) ret_data;
// Allocate memory for joystick state
_glfwJoy[ joy_count ].Axis =
(float *) malloc( sizeof(float) *
_glfwJoy[ joy_count ].NumAxes );
if( _glfwJoy[ joy_count ].Axis == NULL )
{
close( fd );
continue;
}
_glfwJoy[ joy_count ].Button =
(unsigned char *) malloc( sizeof(char) *
_glfwJoy[ joy_count ].NumButtons );
if( _glfwJoy[ joy_count ].Button == NULL )
{
free( _glfwJoy[ joy_count ].Axis );
close( fd );
continue;
}
// Clear joystick state
for( n = 0; n < _glfwJoy[ joy_count ].NumAxes; ++ n )
{
_glfwJoy[ joy_count ].Axis[ n ] = 0.0f;
}
for( n = 0; n < _glfwJoy[ joy_count ].NumButtons; ++ n )
{
_glfwJoy[ joy_count ].Button[ n ] = GLFW_RELEASE;
}
// The joystick is supported and connected
_glfwJoy[ joy_count ].Present = GL_TRUE;
joy_count ++;
}
}
}
#endif // _GLFW_USE_LINUX_JOYSTICKS
}
//========================================================================
// Close all opened joystick handles
//========================================================================
void _glfwTerminateJoysticks( void )
{
#ifdef _GLFW_USE_LINUX_JOYSTICKS
int i;
// Close any opened joysticks
for( i = 0; i <= GLFW_JOYSTICK_LAST; ++ i )
{
if( _glfwJoy[ i ].Present )
{
close( _glfwJoy[ i ].fd );
free( _glfwJoy[ i ].Axis );
free( _glfwJoy[ i ].Button );
_glfwJoy[ i ].Present = GL_FALSE;
}
}
#endif // _GLFW_USE_LINUX_JOYSTICKS
}
//========================================================================
// Empty joystick event queue
//========================================================================
static void pollJoystickEvents( void )
{
#ifdef _GLFW_USE_LINUX_JOYSTICKS
struct js_event e;
int i;
// Get joystick events for all GLFW joysticks
for( i = 0; i <= GLFW_JOYSTICK_LAST; ++ i )
{
// Is the stick present?
if( _glfwJoy[ i ].Present )
{
// Read all queued events (non-blocking)
while( read(_glfwJoy[i].fd, &e, sizeof(struct js_event)) > 0 )
{
// We don't care if it's an init event or not
e.type &= ~JS_EVENT_INIT;
// Check event type
switch( e.type )
{
case JS_EVENT_AXIS:
_glfwJoy[ i ].Axis[ e.number ] = (float) e.value /
32767.0f;
// We need to change the sign for the Y axes, so that
// positive = up/forward, according to the GLFW spec.
if( e.number & 1 )
{
_glfwJoy[ i ].Axis[ e.number ] =
-_glfwJoy[ i ].Axis[ e.number ];
}
break;
case JS_EVENT_BUTTON:
_glfwJoy[ i ].Button[ e.number ] =
e.value ? GLFW_PRESS : GLFW_RELEASE;
break;
default:
break;
}
}
}
}
#endif // _GLFW_USE_LINUX_JOYSTICKS
}
//************************************************************************
//**** Platform implementation functions ****
//************************************************************************
//========================================================================
// Determine joystick capabilities
//========================================================================
int _glfwPlatformGetJoystickParam( int joy, int param )
{
// Is joystick present?
if( !_glfwJoy[ joy ].Present )
{
return 0;
}
switch( param )
{
case GLFW_PRESENT:
return GL_TRUE;
case GLFW_AXES:
return _glfwJoy[ joy ].NumAxes;
case GLFW_BUTTONS:
return _glfwJoy[ joy ].NumButtons;
default:
break;
}
return 0;
}
//========================================================================
// Get joystick axis positions
//========================================================================
int _glfwPlatformGetJoystickPos( int joy, float *pos, int numaxes )
{
int i;
// Is joystick present?
if( !_glfwJoy[ joy ].Present )
{
return 0;
}
// Update joystick state
pollJoystickEvents();
// Does the joystick support less axes than requested?
if( _glfwJoy[ joy ].NumAxes < numaxes )
{
numaxes = _glfwJoy[ joy ].NumAxes;
}
// Copy axis positions from internal state
for( i = 0; i < numaxes; ++ i )
{
pos[ i ] = _glfwJoy[ joy ].Axis[ i ];
}
return numaxes;
}
//========================================================================
// Get joystick button states
//========================================================================
int _glfwPlatformGetJoystickButtons( int joy, unsigned char *buttons,
int numbuttons )
{
int i;
// Is joystick present?
if( !_glfwJoy[ joy ].Present )
{
return 0;
}
// Update joystick state
pollJoystickEvents();
// Does the joystick support less buttons than requested?
if( _glfwJoy[ joy ].NumButtons < numbuttons )
{
numbuttons = _glfwJoy[ joy ].NumButtons;
}
// Copy button states from internal state
for( i = 0; i < numbuttons; ++ i )
{
buttons[ i ] = _glfwJoy[ joy ].Button[ i ];
}
return numbuttons;
}
@@ -0,0 +1,901 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: X11/GLX
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
/*
* Marcus: This code was originally written by Markus G. Kuhn.
* I have made some slight changes (trimmed it down a bit from >60 KB to
* 20 KB), but the functionality is the same.
*/
/*
* This module converts keysym values into the corresponding ISO 10646
* (UCS, Unicode) values.
*
* The array keysymtab[] contains pairs of X11 keysym values for graphical
* characters and the corresponding Unicode value. The function
* _glfwKeySym2Unicode() maps a keysym onto a Unicode value using a binary
* search, therefore keysymtab[] must remain SORTED by keysym value.
*
* We allow to represent any UCS character in the range U-00000000 to
* U-00FFFFFF by a keysym value in the range 0x01000000 to 0x01ffffff.
* This admittedly does not cover the entire 31-bit space of UCS, but
* it does cover all of the characters up to U-10FFFF, which can be
* represented by UTF-16, and more, and it is very unlikely that higher
* UCS codes will ever be assigned by ISO. So to get Unicode character
* U+ABCD you can directly use keysym 0x0100abcd.
*
* Original author: Markus G. Kuhn <mkuhn@acm.org>, University of
* Cambridge, April 2001
*
* Special thanks to Richard Verhoeven <river@win.tue.nl> for preparing
* an initial draft of the mapping table.
*
*/
//************************************************************************
//**** KeySym to Unicode mapping table ****
//************************************************************************
static struct codepair {
unsigned short keysym;
unsigned short ucs;
} keysymtab[] = {
{ 0x01a1, 0x0104 },
{ 0x01a2, 0x02d8 },
{ 0x01a3, 0x0141 },
{ 0x01a5, 0x013d },
{ 0x01a6, 0x015a },
{ 0x01a9, 0x0160 },
{ 0x01aa, 0x015e },
{ 0x01ab, 0x0164 },
{ 0x01ac, 0x0179 },
{ 0x01ae, 0x017d },
{ 0x01af, 0x017b },
{ 0x01b1, 0x0105 },
{ 0x01b2, 0x02db },
{ 0x01b3, 0x0142 },
{ 0x01b5, 0x013e },
{ 0x01b6, 0x015b },
{ 0x01b7, 0x02c7 },
{ 0x01b9, 0x0161 },
{ 0x01ba, 0x015f },
{ 0x01bb, 0x0165 },
{ 0x01bc, 0x017a },
{ 0x01bd, 0x02dd },
{ 0x01be, 0x017e },
{ 0x01bf, 0x017c },
{ 0x01c0, 0x0154 },
{ 0x01c3, 0x0102 },
{ 0x01c5, 0x0139 },
{ 0x01c6, 0x0106 },
{ 0x01c8, 0x010c },
{ 0x01ca, 0x0118 },
{ 0x01cc, 0x011a },
{ 0x01cf, 0x010e },
{ 0x01d0, 0x0110 },
{ 0x01d1, 0x0143 },
{ 0x01d2, 0x0147 },
{ 0x01d5, 0x0150 },
{ 0x01d8, 0x0158 },
{ 0x01d9, 0x016e },
{ 0x01db, 0x0170 },
{ 0x01de, 0x0162 },
{ 0x01e0, 0x0155 },
{ 0x01e3, 0x0103 },
{ 0x01e5, 0x013a },
{ 0x01e6, 0x0107 },
{ 0x01e8, 0x010d },
{ 0x01ea, 0x0119 },
{ 0x01ec, 0x011b },
{ 0x01ef, 0x010f },
{ 0x01f0, 0x0111 },
{ 0x01f1, 0x0144 },
{ 0x01f2, 0x0148 },
{ 0x01f5, 0x0151 },
{ 0x01f8, 0x0159 },
{ 0x01f9, 0x016f },
{ 0x01fb, 0x0171 },
{ 0x01fe, 0x0163 },
{ 0x01ff, 0x02d9 },
{ 0x02a1, 0x0126 },
{ 0x02a6, 0x0124 },
{ 0x02a9, 0x0130 },
{ 0x02ab, 0x011e },
{ 0x02ac, 0x0134 },
{ 0x02b1, 0x0127 },
{ 0x02b6, 0x0125 },
{ 0x02b9, 0x0131 },
{ 0x02bb, 0x011f },
{ 0x02bc, 0x0135 },
{ 0x02c5, 0x010a },
{ 0x02c6, 0x0108 },
{ 0x02d5, 0x0120 },
{ 0x02d8, 0x011c },
{ 0x02dd, 0x016c },
{ 0x02de, 0x015c },
{ 0x02e5, 0x010b },
{ 0x02e6, 0x0109 },
{ 0x02f5, 0x0121 },
{ 0x02f8, 0x011d },
{ 0x02fd, 0x016d },
{ 0x02fe, 0x015d },
{ 0x03a2, 0x0138 },
{ 0x03a3, 0x0156 },
{ 0x03a5, 0x0128 },
{ 0x03a6, 0x013b },
{ 0x03aa, 0x0112 },
{ 0x03ab, 0x0122 },
{ 0x03ac, 0x0166 },
{ 0x03b3, 0x0157 },
{ 0x03b5, 0x0129 },
{ 0x03b6, 0x013c },
{ 0x03ba, 0x0113 },
{ 0x03bb, 0x0123 },
{ 0x03bc, 0x0167 },
{ 0x03bd, 0x014a },
{ 0x03bf, 0x014b },
{ 0x03c0, 0x0100 },
{ 0x03c7, 0x012e },
{ 0x03cc, 0x0116 },
{ 0x03cf, 0x012a },
{ 0x03d1, 0x0145 },
{ 0x03d2, 0x014c },
{ 0x03d3, 0x0136 },
{ 0x03d9, 0x0172 },
{ 0x03dd, 0x0168 },
{ 0x03de, 0x016a },
{ 0x03e0, 0x0101 },
{ 0x03e7, 0x012f },
{ 0x03ec, 0x0117 },
{ 0x03ef, 0x012b },
{ 0x03f1, 0x0146 },
{ 0x03f2, 0x014d },
{ 0x03f3, 0x0137 },
{ 0x03f9, 0x0173 },
{ 0x03fd, 0x0169 },
{ 0x03fe, 0x016b },
{ 0x047e, 0x203e },
{ 0x04a1, 0x3002 },
{ 0x04a2, 0x300c },
{ 0x04a3, 0x300d },
{ 0x04a4, 0x3001 },
{ 0x04a5, 0x30fb },
{ 0x04a6, 0x30f2 },
{ 0x04a7, 0x30a1 },
{ 0x04a8, 0x30a3 },
{ 0x04a9, 0x30a5 },
{ 0x04aa, 0x30a7 },
{ 0x04ab, 0x30a9 },
{ 0x04ac, 0x30e3 },
{ 0x04ad, 0x30e5 },
{ 0x04ae, 0x30e7 },
{ 0x04af, 0x30c3 },
{ 0x04b0, 0x30fc },
{ 0x04b1, 0x30a2 },
{ 0x04b2, 0x30a4 },
{ 0x04b3, 0x30a6 },
{ 0x04b4, 0x30a8 },
{ 0x04b5, 0x30aa },
{ 0x04b6, 0x30ab },
{ 0x04b7, 0x30ad },
{ 0x04b8, 0x30af },
{ 0x04b9, 0x30b1 },
{ 0x04ba, 0x30b3 },
{ 0x04bb, 0x30b5 },
{ 0x04bc, 0x30b7 },
{ 0x04bd, 0x30b9 },
{ 0x04be, 0x30bb },
{ 0x04bf, 0x30bd },
{ 0x04c0, 0x30bf },
{ 0x04c1, 0x30c1 },
{ 0x04c2, 0x30c4 },
{ 0x04c3, 0x30c6 },
{ 0x04c4, 0x30c8 },
{ 0x04c5, 0x30ca },
{ 0x04c6, 0x30cb },
{ 0x04c7, 0x30cc },
{ 0x04c8, 0x30cd },
{ 0x04c9, 0x30ce },
{ 0x04ca, 0x30cf },
{ 0x04cb, 0x30d2 },
{ 0x04cc, 0x30d5 },
{ 0x04cd, 0x30d8 },
{ 0x04ce, 0x30db },
{ 0x04cf, 0x30de },
{ 0x04d0, 0x30df },
{ 0x04d1, 0x30e0 },
{ 0x04d2, 0x30e1 },
{ 0x04d3, 0x30e2 },
{ 0x04d4, 0x30e4 },
{ 0x04d5, 0x30e6 },
{ 0x04d6, 0x30e8 },
{ 0x04d7, 0x30e9 },
{ 0x04d8, 0x30ea },
{ 0x04d9, 0x30eb },
{ 0x04da, 0x30ec },
{ 0x04db, 0x30ed },
{ 0x04dc, 0x30ef },
{ 0x04dd, 0x30f3 },
{ 0x04de, 0x309b },
{ 0x04df, 0x309c },
{ 0x05ac, 0x060c },
{ 0x05bb, 0x061b },
{ 0x05bf, 0x061f },
{ 0x05c1, 0x0621 },
{ 0x05c2, 0x0622 },
{ 0x05c3, 0x0623 },
{ 0x05c4, 0x0624 },
{ 0x05c5, 0x0625 },
{ 0x05c6, 0x0626 },
{ 0x05c7, 0x0627 },
{ 0x05c8, 0x0628 },
{ 0x05c9, 0x0629 },
{ 0x05ca, 0x062a },
{ 0x05cb, 0x062b },
{ 0x05cc, 0x062c },
{ 0x05cd, 0x062d },
{ 0x05ce, 0x062e },
{ 0x05cf, 0x062f },
{ 0x05d0, 0x0630 },
{ 0x05d1, 0x0631 },
{ 0x05d2, 0x0632 },
{ 0x05d3, 0x0633 },
{ 0x05d4, 0x0634 },
{ 0x05d5, 0x0635 },
{ 0x05d6, 0x0636 },
{ 0x05d7, 0x0637 },
{ 0x05d8, 0x0638 },
{ 0x05d9, 0x0639 },
{ 0x05da, 0x063a },
{ 0x05e0, 0x0640 },
{ 0x05e1, 0x0641 },
{ 0x05e2, 0x0642 },
{ 0x05e3, 0x0643 },
{ 0x05e4, 0x0644 },
{ 0x05e5, 0x0645 },
{ 0x05e6, 0x0646 },
{ 0x05e7, 0x0647 },
{ 0x05e8, 0x0648 },
{ 0x05e9, 0x0649 },
{ 0x05ea, 0x064a },
{ 0x05eb, 0x064b },
{ 0x05ec, 0x064c },
{ 0x05ed, 0x064d },
{ 0x05ee, 0x064e },
{ 0x05ef, 0x064f },
{ 0x05f0, 0x0650 },
{ 0x05f1, 0x0651 },
{ 0x05f2, 0x0652 },
{ 0x06a1, 0x0452 },
{ 0x06a2, 0x0453 },
{ 0x06a3, 0x0451 },
{ 0x06a4, 0x0454 },
{ 0x06a5, 0x0455 },
{ 0x06a6, 0x0456 },
{ 0x06a7, 0x0457 },
{ 0x06a8, 0x0458 },
{ 0x06a9, 0x0459 },
{ 0x06aa, 0x045a },
{ 0x06ab, 0x045b },
{ 0x06ac, 0x045c },
{ 0x06ae, 0x045e },
{ 0x06af, 0x045f },
{ 0x06b0, 0x2116 },
{ 0x06b1, 0x0402 },
{ 0x06b2, 0x0403 },
{ 0x06b3, 0x0401 },
{ 0x06b4, 0x0404 },
{ 0x06b5, 0x0405 },
{ 0x06b6, 0x0406 },
{ 0x06b7, 0x0407 },
{ 0x06b8, 0x0408 },
{ 0x06b9, 0x0409 },
{ 0x06ba, 0x040a },
{ 0x06bb, 0x040b },
{ 0x06bc, 0x040c },
{ 0x06be, 0x040e },
{ 0x06bf, 0x040f },
{ 0x06c0, 0x044e },
{ 0x06c1, 0x0430 },
{ 0x06c2, 0x0431 },
{ 0x06c3, 0x0446 },
{ 0x06c4, 0x0434 },
{ 0x06c5, 0x0435 },
{ 0x06c6, 0x0444 },
{ 0x06c7, 0x0433 },
{ 0x06c8, 0x0445 },
{ 0x06c9, 0x0438 },
{ 0x06ca, 0x0439 },
{ 0x06cb, 0x043a },
{ 0x06cc, 0x043b },
{ 0x06cd, 0x043c },
{ 0x06ce, 0x043d },
{ 0x06cf, 0x043e },
{ 0x06d0, 0x043f },
{ 0x06d1, 0x044f },
{ 0x06d2, 0x0440 },
{ 0x06d3, 0x0441 },
{ 0x06d4, 0x0442 },
{ 0x06d5, 0x0443 },
{ 0x06d6, 0x0436 },
{ 0x06d7, 0x0432 },
{ 0x06d8, 0x044c },
{ 0x06d9, 0x044b },
{ 0x06da, 0x0437 },
{ 0x06db, 0x0448 },
{ 0x06dc, 0x044d },
{ 0x06dd, 0x0449 },
{ 0x06de, 0x0447 },
{ 0x06df, 0x044a },
{ 0x06e0, 0x042e },
{ 0x06e1, 0x0410 },
{ 0x06e2, 0x0411 },
{ 0x06e3, 0x0426 },
{ 0x06e4, 0x0414 },
{ 0x06e5, 0x0415 },
{ 0x06e6, 0x0424 },
{ 0x06e7, 0x0413 },
{ 0x06e8, 0x0425 },
{ 0x06e9, 0x0418 },
{ 0x06ea, 0x0419 },
{ 0x06eb, 0x041a },
{ 0x06ec, 0x041b },
{ 0x06ed, 0x041c },
{ 0x06ee, 0x041d },
{ 0x06ef, 0x041e },
{ 0x06f0, 0x041f },
{ 0x06f1, 0x042f },
{ 0x06f2, 0x0420 },
{ 0x06f3, 0x0421 },
{ 0x06f4, 0x0422 },
{ 0x06f5, 0x0423 },
{ 0x06f6, 0x0416 },
{ 0x06f7, 0x0412 },
{ 0x06f8, 0x042c },
{ 0x06f9, 0x042b },
{ 0x06fa, 0x0417 },
{ 0x06fb, 0x0428 },
{ 0x06fc, 0x042d },
{ 0x06fd, 0x0429 },
{ 0x06fe, 0x0427 },
{ 0x06ff, 0x042a },
{ 0x07a1, 0x0386 },
{ 0x07a2, 0x0388 },
{ 0x07a3, 0x0389 },
{ 0x07a4, 0x038a },
{ 0x07a5, 0x03aa },
{ 0x07a7, 0x038c },
{ 0x07a8, 0x038e },
{ 0x07a9, 0x03ab },
{ 0x07ab, 0x038f },
{ 0x07ae, 0x0385 },
{ 0x07af, 0x2015 },
{ 0x07b1, 0x03ac },
{ 0x07b2, 0x03ad },
{ 0x07b3, 0x03ae },
{ 0x07b4, 0x03af },
{ 0x07b5, 0x03ca },
{ 0x07b6, 0x0390 },
{ 0x07b7, 0x03cc },
{ 0x07b8, 0x03cd },
{ 0x07b9, 0x03cb },
{ 0x07ba, 0x03b0 },
{ 0x07bb, 0x03ce },
{ 0x07c1, 0x0391 },
{ 0x07c2, 0x0392 },
{ 0x07c3, 0x0393 },
{ 0x07c4, 0x0394 },
{ 0x07c5, 0x0395 },
{ 0x07c6, 0x0396 },
{ 0x07c7, 0x0397 },
{ 0x07c8, 0x0398 },
{ 0x07c9, 0x0399 },
{ 0x07ca, 0x039a },
{ 0x07cb, 0x039b },
{ 0x07cc, 0x039c },
{ 0x07cd, 0x039d },
{ 0x07ce, 0x039e },
{ 0x07cf, 0x039f },
{ 0x07d0, 0x03a0 },
{ 0x07d1, 0x03a1 },
{ 0x07d2, 0x03a3 },
{ 0x07d4, 0x03a4 },
{ 0x07d5, 0x03a5 },
{ 0x07d6, 0x03a6 },
{ 0x07d7, 0x03a7 },
{ 0x07d8, 0x03a8 },
{ 0x07d9, 0x03a9 },
{ 0x07e1, 0x03b1 },
{ 0x07e2, 0x03b2 },
{ 0x07e3, 0x03b3 },
{ 0x07e4, 0x03b4 },
{ 0x07e5, 0x03b5 },
{ 0x07e6, 0x03b6 },
{ 0x07e7, 0x03b7 },
{ 0x07e8, 0x03b8 },
{ 0x07e9, 0x03b9 },
{ 0x07ea, 0x03ba },
{ 0x07eb, 0x03bb },
{ 0x07ec, 0x03bc },
{ 0x07ed, 0x03bd },
{ 0x07ee, 0x03be },
{ 0x07ef, 0x03bf },
{ 0x07f0, 0x03c0 },
{ 0x07f1, 0x03c1 },
{ 0x07f2, 0x03c3 },
{ 0x07f3, 0x03c2 },
{ 0x07f4, 0x03c4 },
{ 0x07f5, 0x03c5 },
{ 0x07f6, 0x03c6 },
{ 0x07f7, 0x03c7 },
{ 0x07f8, 0x03c8 },
{ 0x07f9, 0x03c9 },
{ 0x08a1, 0x23b7 },
{ 0x08a2, 0x250c },
{ 0x08a3, 0x2500 },
{ 0x08a4, 0x2320 },
{ 0x08a5, 0x2321 },
{ 0x08a6, 0x2502 },
{ 0x08a7, 0x23a1 },
{ 0x08a8, 0x23a3 },
{ 0x08a9, 0x23a4 },
{ 0x08aa, 0x23a6 },
{ 0x08ab, 0x239b },
{ 0x08ac, 0x239d },
{ 0x08ad, 0x239e },
{ 0x08ae, 0x23a0 },
{ 0x08af, 0x23a8 },
{ 0x08b0, 0x23ac },
{ 0x08bc, 0x2264 },
{ 0x08bd, 0x2260 },
{ 0x08be, 0x2265 },
{ 0x08bf, 0x222b },
{ 0x08c0, 0x2234 },
{ 0x08c1, 0x221d },
{ 0x08c2, 0x221e },
{ 0x08c5, 0x2207 },
{ 0x08c8, 0x223c },
{ 0x08c9, 0x2243 },
{ 0x08cd, 0x21d4 },
{ 0x08ce, 0x21d2 },
{ 0x08cf, 0x2261 },
{ 0x08d6, 0x221a },
{ 0x08da, 0x2282 },
{ 0x08db, 0x2283 },
{ 0x08dc, 0x2229 },
{ 0x08dd, 0x222a },
{ 0x08de, 0x2227 },
{ 0x08df, 0x2228 },
{ 0x08ef, 0x2202 },
{ 0x08f6, 0x0192 },
{ 0x08fb, 0x2190 },
{ 0x08fc, 0x2191 },
{ 0x08fd, 0x2192 },
{ 0x08fe, 0x2193 },
{ 0x09e0, 0x25c6 },
{ 0x09e1, 0x2592 },
{ 0x09e2, 0x2409 },
{ 0x09e3, 0x240c },
{ 0x09e4, 0x240d },
{ 0x09e5, 0x240a },
{ 0x09e8, 0x2424 },
{ 0x09e9, 0x240b },
{ 0x09ea, 0x2518 },
{ 0x09eb, 0x2510 },
{ 0x09ec, 0x250c },
{ 0x09ed, 0x2514 },
{ 0x09ee, 0x253c },
{ 0x09ef, 0x23ba },
{ 0x09f0, 0x23bb },
{ 0x09f1, 0x2500 },
{ 0x09f2, 0x23bc },
{ 0x09f3, 0x23bd },
{ 0x09f4, 0x251c },
{ 0x09f5, 0x2524 },
{ 0x09f6, 0x2534 },
{ 0x09f7, 0x252c },
{ 0x09f8, 0x2502 },
{ 0x0aa1, 0x2003 },
{ 0x0aa2, 0x2002 },
{ 0x0aa3, 0x2004 },
{ 0x0aa4, 0x2005 },
{ 0x0aa5, 0x2007 },
{ 0x0aa6, 0x2008 },
{ 0x0aa7, 0x2009 },
{ 0x0aa8, 0x200a },
{ 0x0aa9, 0x2014 },
{ 0x0aaa, 0x2013 },
{ 0x0aae, 0x2026 },
{ 0x0aaf, 0x2025 },
{ 0x0ab0, 0x2153 },
{ 0x0ab1, 0x2154 },
{ 0x0ab2, 0x2155 },
{ 0x0ab3, 0x2156 },
{ 0x0ab4, 0x2157 },
{ 0x0ab5, 0x2158 },
{ 0x0ab6, 0x2159 },
{ 0x0ab7, 0x215a },
{ 0x0ab8, 0x2105 },
{ 0x0abb, 0x2012 },
{ 0x0abc, 0x2329 },
{ 0x0abe, 0x232a },
{ 0x0ac3, 0x215b },
{ 0x0ac4, 0x215c },
{ 0x0ac5, 0x215d },
{ 0x0ac6, 0x215e },
{ 0x0ac9, 0x2122 },
{ 0x0aca, 0x2613 },
{ 0x0acc, 0x25c1 },
{ 0x0acd, 0x25b7 },
{ 0x0ace, 0x25cb },
{ 0x0acf, 0x25af },
{ 0x0ad0, 0x2018 },
{ 0x0ad1, 0x2019 },
{ 0x0ad2, 0x201c },
{ 0x0ad3, 0x201d },
{ 0x0ad4, 0x211e },
{ 0x0ad6, 0x2032 },
{ 0x0ad7, 0x2033 },
{ 0x0ad9, 0x271d },
{ 0x0adb, 0x25ac },
{ 0x0adc, 0x25c0 },
{ 0x0add, 0x25b6 },
{ 0x0ade, 0x25cf },
{ 0x0adf, 0x25ae },
{ 0x0ae0, 0x25e6 },
{ 0x0ae1, 0x25ab },
{ 0x0ae2, 0x25ad },
{ 0x0ae3, 0x25b3 },
{ 0x0ae4, 0x25bd },
{ 0x0ae5, 0x2606 },
{ 0x0ae6, 0x2022 },
{ 0x0ae7, 0x25aa },
{ 0x0ae8, 0x25b2 },
{ 0x0ae9, 0x25bc },
{ 0x0aea, 0x261c },
{ 0x0aeb, 0x261e },
{ 0x0aec, 0x2663 },
{ 0x0aed, 0x2666 },
{ 0x0aee, 0x2665 },
{ 0x0af0, 0x2720 },
{ 0x0af1, 0x2020 },
{ 0x0af2, 0x2021 },
{ 0x0af3, 0x2713 },
{ 0x0af4, 0x2717 },
{ 0x0af5, 0x266f },
{ 0x0af6, 0x266d },
{ 0x0af7, 0x2642 },
{ 0x0af8, 0x2640 },
{ 0x0af9, 0x260e },
{ 0x0afa, 0x2315 },
{ 0x0afb, 0x2117 },
{ 0x0afc, 0x2038 },
{ 0x0afd, 0x201a },
{ 0x0afe, 0x201e },
{ 0x0ba3, 0x003c },
{ 0x0ba6, 0x003e },
{ 0x0ba8, 0x2228 },
{ 0x0ba9, 0x2227 },
{ 0x0bc0, 0x00af },
{ 0x0bc2, 0x22a5 },
{ 0x0bc3, 0x2229 },
{ 0x0bc4, 0x230a },
{ 0x0bc6, 0x005f },
{ 0x0bca, 0x2218 },
{ 0x0bcc, 0x2395 },
{ 0x0bce, 0x22a4 },
{ 0x0bcf, 0x25cb },
{ 0x0bd3, 0x2308 },
{ 0x0bd6, 0x222a },
{ 0x0bd8, 0x2283 },
{ 0x0bda, 0x2282 },
{ 0x0bdc, 0x22a2 },
{ 0x0bfc, 0x22a3 },
{ 0x0cdf, 0x2017 },
{ 0x0ce0, 0x05d0 },
{ 0x0ce1, 0x05d1 },
{ 0x0ce2, 0x05d2 },
{ 0x0ce3, 0x05d3 },
{ 0x0ce4, 0x05d4 },
{ 0x0ce5, 0x05d5 },
{ 0x0ce6, 0x05d6 },
{ 0x0ce7, 0x05d7 },
{ 0x0ce8, 0x05d8 },
{ 0x0ce9, 0x05d9 },
{ 0x0cea, 0x05da },
{ 0x0ceb, 0x05db },
{ 0x0cec, 0x05dc },
{ 0x0ced, 0x05dd },
{ 0x0cee, 0x05de },
{ 0x0cef, 0x05df },
{ 0x0cf0, 0x05e0 },
{ 0x0cf1, 0x05e1 },
{ 0x0cf2, 0x05e2 },
{ 0x0cf3, 0x05e3 },
{ 0x0cf4, 0x05e4 },
{ 0x0cf5, 0x05e5 },
{ 0x0cf6, 0x05e6 },
{ 0x0cf7, 0x05e7 },
{ 0x0cf8, 0x05e8 },
{ 0x0cf9, 0x05e9 },
{ 0x0cfa, 0x05ea },
{ 0x0da1, 0x0e01 },
{ 0x0da2, 0x0e02 },
{ 0x0da3, 0x0e03 },
{ 0x0da4, 0x0e04 },
{ 0x0da5, 0x0e05 },
{ 0x0da6, 0x0e06 },
{ 0x0da7, 0x0e07 },
{ 0x0da8, 0x0e08 },
{ 0x0da9, 0x0e09 },
{ 0x0daa, 0x0e0a },
{ 0x0dab, 0x0e0b },
{ 0x0dac, 0x0e0c },
{ 0x0dad, 0x0e0d },
{ 0x0dae, 0x0e0e },
{ 0x0daf, 0x0e0f },
{ 0x0db0, 0x0e10 },
{ 0x0db1, 0x0e11 },
{ 0x0db2, 0x0e12 },
{ 0x0db3, 0x0e13 },
{ 0x0db4, 0x0e14 },
{ 0x0db5, 0x0e15 },
{ 0x0db6, 0x0e16 },
{ 0x0db7, 0x0e17 },
{ 0x0db8, 0x0e18 },
{ 0x0db9, 0x0e19 },
{ 0x0dba, 0x0e1a },
{ 0x0dbb, 0x0e1b },
{ 0x0dbc, 0x0e1c },
{ 0x0dbd, 0x0e1d },
{ 0x0dbe, 0x0e1e },
{ 0x0dbf, 0x0e1f },
{ 0x0dc0, 0x0e20 },
{ 0x0dc1, 0x0e21 },
{ 0x0dc2, 0x0e22 },
{ 0x0dc3, 0x0e23 },
{ 0x0dc4, 0x0e24 },
{ 0x0dc5, 0x0e25 },
{ 0x0dc6, 0x0e26 },
{ 0x0dc7, 0x0e27 },
{ 0x0dc8, 0x0e28 },
{ 0x0dc9, 0x0e29 },
{ 0x0dca, 0x0e2a },
{ 0x0dcb, 0x0e2b },
{ 0x0dcc, 0x0e2c },
{ 0x0dcd, 0x0e2d },
{ 0x0dce, 0x0e2e },
{ 0x0dcf, 0x0e2f },
{ 0x0dd0, 0x0e30 },
{ 0x0dd1, 0x0e31 },
{ 0x0dd2, 0x0e32 },
{ 0x0dd3, 0x0e33 },
{ 0x0dd4, 0x0e34 },
{ 0x0dd5, 0x0e35 },
{ 0x0dd6, 0x0e36 },
{ 0x0dd7, 0x0e37 },
{ 0x0dd8, 0x0e38 },
{ 0x0dd9, 0x0e39 },
{ 0x0dda, 0x0e3a },
{ 0x0ddf, 0x0e3f },
{ 0x0de0, 0x0e40 },
{ 0x0de1, 0x0e41 },
{ 0x0de2, 0x0e42 },
{ 0x0de3, 0x0e43 },
{ 0x0de4, 0x0e44 },
{ 0x0de5, 0x0e45 },
{ 0x0de6, 0x0e46 },
{ 0x0de7, 0x0e47 },
{ 0x0de8, 0x0e48 },
{ 0x0de9, 0x0e49 },
{ 0x0dea, 0x0e4a },
{ 0x0deb, 0x0e4b },
{ 0x0dec, 0x0e4c },
{ 0x0ded, 0x0e4d },
{ 0x0df0, 0x0e50 },
{ 0x0df1, 0x0e51 },
{ 0x0df2, 0x0e52 },
{ 0x0df3, 0x0e53 },
{ 0x0df4, 0x0e54 },
{ 0x0df5, 0x0e55 },
{ 0x0df6, 0x0e56 },
{ 0x0df7, 0x0e57 },
{ 0x0df8, 0x0e58 },
{ 0x0df9, 0x0e59 },
{ 0x0ea1, 0x3131 },
{ 0x0ea2, 0x3132 },
{ 0x0ea3, 0x3133 },
{ 0x0ea4, 0x3134 },
{ 0x0ea5, 0x3135 },
{ 0x0ea6, 0x3136 },
{ 0x0ea7, 0x3137 },
{ 0x0ea8, 0x3138 },
{ 0x0ea9, 0x3139 },
{ 0x0eaa, 0x313a },
{ 0x0eab, 0x313b },
{ 0x0eac, 0x313c },
{ 0x0ead, 0x313d },
{ 0x0eae, 0x313e },
{ 0x0eaf, 0x313f },
{ 0x0eb0, 0x3140 },
{ 0x0eb1, 0x3141 },
{ 0x0eb2, 0x3142 },
{ 0x0eb3, 0x3143 },
{ 0x0eb4, 0x3144 },
{ 0x0eb5, 0x3145 },
{ 0x0eb6, 0x3146 },
{ 0x0eb7, 0x3147 },
{ 0x0eb8, 0x3148 },
{ 0x0eb9, 0x3149 },
{ 0x0eba, 0x314a },
{ 0x0ebb, 0x314b },
{ 0x0ebc, 0x314c },
{ 0x0ebd, 0x314d },
{ 0x0ebe, 0x314e },
{ 0x0ebf, 0x314f },
{ 0x0ec0, 0x3150 },
{ 0x0ec1, 0x3151 },
{ 0x0ec2, 0x3152 },
{ 0x0ec3, 0x3153 },
{ 0x0ec4, 0x3154 },
{ 0x0ec5, 0x3155 },
{ 0x0ec6, 0x3156 },
{ 0x0ec7, 0x3157 },
{ 0x0ec8, 0x3158 },
{ 0x0ec9, 0x3159 },
{ 0x0eca, 0x315a },
{ 0x0ecb, 0x315b },
{ 0x0ecc, 0x315c },
{ 0x0ecd, 0x315d },
{ 0x0ece, 0x315e },
{ 0x0ecf, 0x315f },
{ 0x0ed0, 0x3160 },
{ 0x0ed1, 0x3161 },
{ 0x0ed2, 0x3162 },
{ 0x0ed3, 0x3163 },
{ 0x0ed4, 0x11a8 },
{ 0x0ed5, 0x11a9 },
{ 0x0ed6, 0x11aa },
{ 0x0ed7, 0x11ab },
{ 0x0ed8, 0x11ac },
{ 0x0ed9, 0x11ad },
{ 0x0eda, 0x11ae },
{ 0x0edb, 0x11af },
{ 0x0edc, 0x11b0 },
{ 0x0edd, 0x11b1 },
{ 0x0ede, 0x11b2 },
{ 0x0edf, 0x11b3 },
{ 0x0ee0, 0x11b4 },
{ 0x0ee1, 0x11b5 },
{ 0x0ee2, 0x11b6 },
{ 0x0ee3, 0x11b7 },
{ 0x0ee4, 0x11b8 },
{ 0x0ee5, 0x11b9 },
{ 0x0ee6, 0x11ba },
{ 0x0ee7, 0x11bb },
{ 0x0ee8, 0x11bc },
{ 0x0ee9, 0x11bd },
{ 0x0eea, 0x11be },
{ 0x0eeb, 0x11bf },
{ 0x0eec, 0x11c0 },
{ 0x0eed, 0x11c1 },
{ 0x0eee, 0x11c2 },
{ 0x0eef, 0x316d },
{ 0x0ef0, 0x3171 },
{ 0x0ef1, 0x3178 },
{ 0x0ef2, 0x317f },
{ 0x0ef3, 0x3181 },
{ 0x0ef4, 0x3184 },
{ 0x0ef5, 0x3186 },
{ 0x0ef6, 0x318d },
{ 0x0ef7, 0x318e },
{ 0x0ef8, 0x11eb },
{ 0x0ef9, 0x11f0 },
{ 0x0efa, 0x11f9 },
{ 0x0eff, 0x20a9 },
{ 0x13a4, 0x20ac },
{ 0x13bc, 0x0152 },
{ 0x13bd, 0x0153 },
{ 0x13be, 0x0178 },
{ 0x20ac, 0x20ac },
// Numeric keypad with numlock on
{ XK_KP_Space, ' ' },
{ XK_KP_Equal, '=' },
{ XK_KP_Multiply, '*' },
{ XK_KP_Add, '+' },
{ XK_KP_Separator, ',' },
{ XK_KP_Subtract, '-' },
{ XK_KP_Decimal, '.' },
{ XK_KP_Divide, '/' },
{ XK_KP_0, 0x0030 },
{ XK_KP_1, 0x0031 },
{ XK_KP_2, 0x0032 },
{ XK_KP_3, 0x0033 },
{ XK_KP_4, 0x0034 },
{ XK_KP_5, 0x0035 },
{ XK_KP_6, 0x0036 },
{ XK_KP_7, 0x0037 },
{ XK_KP_8, 0x0038 },
{ XK_KP_9, 0x0039 }
};
//************************************************************************
//**** GLFW internal functions ****
//************************************************************************
//========================================================================
// Convert X11 KeySym to Unicode
//========================================================================
long _glfwKeySym2Unicode( KeySym keysym )
{
int min = 0;
int max = sizeof(keysymtab) / sizeof(struct codepair) - 1;
int mid;
/* First check for Latin-1 characters (1:1 mapping) */
if( (keysym >= 0x0020 && keysym <= 0x007e) ||
(keysym >= 0x00a0 && keysym <= 0x00ff) )
{ return keysym;
}
/* Also check for directly encoded 24-bit UCS characters */
if( (keysym & 0xff000000) == 0x01000000 )
{
return keysym & 0x00ffffff;
}
/* Binary search in table */
while( max >= min )
{
mid = (min + max) / 2;
if( keysymtab[mid].keysym < keysym )
{
min = mid + 1;
}
else if( keysymtab[mid].keysym > keysym )
{
max = mid - 1;
}
else
{
/* Found it! */
return keysymtab[mid].ucs;
}
}
/* No matching Unicode value found */
return -1;
}
+503
View File
@@ -0,0 +1,503 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: X11/GLX
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
//************************************************************************
//**** GLFW internal functions ****
//************************************************************************
#ifdef _GLFW_HAS_PTHREAD
//========================================================================
// This is simply a "wrapper" for calling the user thread function.
//========================================================================
void * _glfwNewThread( void * arg )
{
GLFWthreadfun threadfun;
_GLFWthread *t;
pthread_t posixID;
// Get current thread ID
posixID = pthread_self();
// Enter critical section
ENTER_THREAD_CRITICAL_SECTION
// Loop through entire list of threads to find the matching POSIX
// thread ID
for( t = &_glfwThrd.First; t != NULL; t = t->Next )
{
if( t->PosixID == posixID )
{
break;
}
}
if( t == NULL )
{
LEAVE_THREAD_CRITICAL_SECTION
return NULL;
}
// Get user thread function pointer
threadfun = t->Function;
// Leave critical section
LEAVE_THREAD_CRITICAL_SECTION
// Call the user thread function
threadfun( arg );
// Remove thread from thread list
ENTER_THREAD_CRITICAL_SECTION
_glfwRemoveThread( t );
LEAVE_THREAD_CRITICAL_SECTION
// When the thread function returns, the thread will die...
return NULL;
}
#endif // _GLFW_HAS_PTHREAD
//************************************************************************
//**** Platform implementation functions ****
//************************************************************************
//========================================================================
// Create a new thread
//========================================================================
GLFWthread _glfwPlatformCreateThread( GLFWthreadfun fun, void *arg )
{
#ifdef _GLFW_HAS_PTHREAD
GLFWthread ID;
_GLFWthread *t;
int result;
// Enter critical section
ENTER_THREAD_CRITICAL_SECTION
// Create a new thread information memory area
t = (_GLFWthread *) malloc( sizeof(_GLFWthread) );
if( t == NULL )
{
// Leave critical section
LEAVE_THREAD_CRITICAL_SECTION
return -1;
}
// Get a new unique thread id
ID = _glfwThrd.NextID ++;
// Store thread information in the thread list
t->Function = fun;
t->ID = ID;
// Create thread
result = pthread_create(
&t->PosixID, // Thread handle
NULL, // Default thread attributes
_glfwNewThread, // Thread function (a wrapper function)
(void *)arg // Argument to thread is user argument
);
// Did the thread creation fail?
if( result != 0 )
{
free( (void *) t );
LEAVE_THREAD_CRITICAL_SECTION
return -1;
}
// Append thread to thread list
_glfwAppendThread( t );
// Leave critical section
LEAVE_THREAD_CRITICAL_SECTION
// Return the GLFW thread ID
return ID;
#else
return -1;
#endif // _GLFW_HAS_PTHREAD
}
//========================================================================
// Kill a thread. NOTE: THIS IS A VERY DANGEROUS OPERATION, AND SHOULD NOT
// BE USED EXCEPT IN EXTREME SITUATIONS!
//========================================================================
void _glfwPlatformDestroyThread( GLFWthread ID )
{
#ifdef _GLFW_HAS_PTHREAD
_GLFWthread *t;
// Enter critical section
ENTER_THREAD_CRITICAL_SECTION
// Get thread information pointer
t = _glfwGetThreadPointer( ID );
if( t == NULL )
{
LEAVE_THREAD_CRITICAL_SECTION
return;
}
// Simply murder the process, no mercy!
pthread_kill( t->PosixID, SIGKILL );
// Remove thread from thread list
_glfwRemoveThread( t );
// Leave critical section
LEAVE_THREAD_CRITICAL_SECTION
#endif // _GLFW_HAS_PTHREAD
}
//========================================================================
// Wait for a thread to die
//========================================================================
int _glfwPlatformWaitThread( GLFWthread ID, int waitmode )
{
#ifdef _GLFW_HAS_PTHREAD
pthread_t thread;
_GLFWthread *t;
// Enter critical section
ENTER_THREAD_CRITICAL_SECTION
// Get thread information pointer
t = _glfwGetThreadPointer( ID );
// Is the thread already dead?
if( t == NULL )
{
LEAVE_THREAD_CRITICAL_SECTION
return GL_TRUE;
}
// If got this far, the thread is alive => polling returns FALSE
if( waitmode == GLFW_NOWAIT )
{
LEAVE_THREAD_CRITICAL_SECTION
return GL_FALSE;
}
// Get thread handle
thread = t->PosixID;
// Leave critical section
LEAVE_THREAD_CRITICAL_SECTION
// Wait for thread to die
(void) pthread_join( thread, NULL );
return GL_TRUE;
#else
return GL_TRUE;
#endif // _GLFW_HAS_PTHREAD
}
//========================================================================
// Return the thread ID for the current thread
//========================================================================
GLFWthread _glfwPlatformGetThreadID( void )
{
#ifdef _GLFW_HAS_PTHREAD
_GLFWthread *t;
GLFWthread ID = -1;
pthread_t posixID;
// Get current thread ID
posixID = pthread_self();
// Enter critical section
ENTER_THREAD_CRITICAL_SECTION
// Loop through entire list of threads to find the matching POSIX
// thread ID
for( t = &_glfwThrd.First; t != NULL; t = t->Next )
{
if( t->PosixID == posixID )
{
ID = t->ID;
break;
}
}
// Leave critical section
LEAVE_THREAD_CRITICAL_SECTION
// Return the found GLFW thread identifier
return ID;
#else
return 0;
#endif // _GLFW_HAS_PTHREAD
}
//========================================================================
// Create a mutual exclusion object
//========================================================================
GLFWmutex _glfwPlatformCreateMutex( void )
{
#ifdef _GLFW_HAS_PTHREAD
pthread_mutex_t *mutex;
// Allocate memory for mutex
mutex = (pthread_mutex_t *) malloc( sizeof( pthread_mutex_t ) );
if( !mutex )
{
return NULL;
}
// Initialise a mutex object
(void) pthread_mutex_init( mutex, NULL );
// Cast to GLFWmutex and return
return (GLFWmutex) mutex;
#else
return (GLFWmutex) 0;
#endif // _GLFW_HAS_PTHREAD
}
//========================================================================
// Destroy a mutual exclusion object
//========================================================================
void _glfwPlatformDestroyMutex( GLFWmutex mutex )
{
#ifdef _GLFW_HAS_PTHREAD
// Destroy the mutex object
pthread_mutex_destroy( (pthread_mutex_t *) mutex );
// Free memory for mutex object
free( (void *) mutex );
#endif // _GLFW_HAS_PTHREAD
}
//========================================================================
// Request access to a mutex
//========================================================================
void _glfwPlatformLockMutex( GLFWmutex mutex )
{
#ifdef _GLFW_HAS_PTHREAD
// Wait for mutex to be released
(void) pthread_mutex_lock( (pthread_mutex_t *) mutex );
#endif // _GLFW_HAS_PTHREAD
}
//========================================================================
// Release a mutex
//========================================================================
void _glfwPlatformUnlockMutex( GLFWmutex mutex )
{
#ifdef _GLFW_HAS_PTHREAD
// Release mutex
pthread_mutex_unlock( (pthread_mutex_t *) mutex );
#endif // _GLFW_HAS_PTHREAD
}
//========================================================================
// Create a new condition variable object
//========================================================================
GLFWcond _glfwPlatformCreateCond( void )
{
#ifdef _GLFW_HAS_PTHREAD
pthread_cond_t *cond;
// Allocate memory for condition variable
cond = (pthread_cond_t *) malloc( sizeof(pthread_cond_t) );
if( !cond )
{
return NULL;
}
// Initialise condition variable
(void) pthread_cond_init( cond, NULL );
// Cast to GLFWcond and return
return (GLFWcond) cond;
#else
return (GLFWcond) 0;
#endif // _GLFW_HAS_PTHREAD
}
//========================================================================
// Destroy a condition variable object
//========================================================================
void _glfwPlatformDestroyCond( GLFWcond cond )
{
#ifdef _GLFW_HAS_PTHREAD
// Destroy the condition variable object
(void) pthread_cond_destroy( (pthread_cond_t *) cond );
// Free memory for condition variable object
free( (void *) cond );
#endif // _GLFW_HAS_PTHREAD
}
//========================================================================
// Wait for a condition to be raised
//========================================================================
void _glfwPlatformWaitCond( GLFWcond cond, GLFWmutex mutex,
double timeout )
{
#ifdef _GLFW_HAS_PTHREAD
struct timeval currenttime;
struct timespec wait;
long dt_sec, dt_usec;
// Select infinite or timed wait
if( timeout >= GLFW_INFINITY )
{
// Wait for condition (infinite wait)
(void) pthread_cond_wait( (pthread_cond_t *) cond,
(pthread_mutex_t *) mutex );
}
else
{
// Set timeout time, relatvie to current time
gettimeofday( &currenttime, NULL );
dt_sec = (long) timeout;
dt_usec = (long) ((timeout - (double)dt_sec) * 1000000.0);
wait.tv_nsec = (currenttime.tv_usec + dt_usec) * 1000L;
if( wait.tv_nsec > 1000000000L )
{
wait.tv_nsec -= 1000000000L;
dt_sec ++;
}
wait.tv_sec = currenttime.tv_sec + dt_sec;
// Wait for condition (timed wait)
(void) pthread_cond_timedwait( (pthread_cond_t *) cond,
(pthread_mutex_t *) mutex, &wait );
}
#endif // _GLFW_HAS_PTHREAD
}
//========================================================================
// Signal a condition to one waiting thread
//========================================================================
void _glfwPlatformSignalCond( GLFWcond cond )
{
#ifdef _GLFW_HAS_PTHREAD
// Signal condition
(void) pthread_cond_signal( (pthread_cond_t *) cond );
#endif // _GLFW_HAS_PTHREAD
}
//========================================================================
// Broadcast a condition to all waiting threads
//========================================================================
void _glfwPlatformBroadcastCond( GLFWcond cond )
{
#ifdef _GLFW_HAS_PTHREAD
// Broadcast condition
(void) pthread_cond_broadcast( (pthread_cond_t *) cond );
#endif // _GLFW_HAS_PTHREAD
}
//========================================================================
// Return the number of processors in the system.
//========================================================================
int _glfwPlatformGetNumberOfProcessors( void )
{
int n;
// Get number of processors online
_glfw_numprocessors( n );
return n;
}
+174
View File
@@ -0,0 +1,174 @@
//========================================================================
// GLFW - An OpenGL framework
// Platform: X11/GLX
// API version: 2.7
// WWW: http://www.glfw.org/
//------------------------------------------------------------------------
// Copyright (c) 2002-2006 Marcus Geelnard
// Copyright (c) 2006-2010 Camilla Berglund <elmindreda@elmindreda.org>
//
// This software is provided 'as-is', without any express or implied
// warranty. In no event will the authors be held liable for any damages
// arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it
// freely, subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented; you must not
// claim that you wrote the original software. If you use this software
// in a product, an acknowledgment in the product documentation would
// be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such, and must not
// be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source
// distribution.
//
//========================================================================
#include "internal.h"
#include <time.h>
//========================================================================
// Return raw time
//========================================================================
static uint64_t getRawTime(void)
{
#if defined( CLOCK_MONOTONIC )
if( _glfwLibrary.Timer.monotonic )
{
struct timespec ts;
clock_gettime( CLOCK_MONOTONIC, &ts );
return (uint64_t) ts.tv_sec * (uint64_t) 1000000000 + (uint64_t) ts.tv_nsec;
}
else
#endif
{
struct timeval tv;
gettimeofday( &tv, NULL );
return (uint64_t) tv.tv_sec * (uint64_t) 1000000 + (uint64_t) tv.tv_usec;
}
}
//========================================================================
// Initialise timer
//========================================================================
void _glfwInitTimer( void )
{
#if defined( CLOCK_MONOTONIC )
struct timespec ts;
if( clock_gettime( CLOCK_MONOTONIC, &ts ) == 0 )
{
_glfwLibrary.Timer.monotonic = GL_TRUE;
_glfwLibrary.Timer.resolution = 1e-9;
}
else
#endif
{
_glfwLibrary.Timer.resolution = 1e-6;
}
_glfwLibrary.Timer.base = getRawTime();
}
//************************************************************************
//**** Platform implementation functions ****
//************************************************************************
//========================================================================
// Return timer value in seconds
//========================================================================
double _glfwPlatformGetTime( void )
{
return (double) (getRawTime() - _glfwLibrary.Timer.base) *
_glfwLibrary.Timer.resolution;
}
//========================================================================
// Set timer value in seconds
//========================================================================
void _glfwPlatformSetTime( double time )
{
_glfwLibrary.Timer.base = getRawTime() -
(uint64_t) (time / _glfwLibrary.Timer.resolution);
}
//========================================================================
// Put a thread to sleep for a specified amount of time
//========================================================================
void _glfwPlatformSleep( double time )
{
#ifdef _GLFW_HAS_PTHREAD
if( time == 0.0 )
{
#ifdef _GLFW_HAS_SCHED_YIELD
sched_yield();
#endif
return;
}
struct timeval currenttime;
struct timespec wait;
pthread_mutex_t mutex;
pthread_cond_t cond;
long dt_sec, dt_usec;
// Not all pthread implementations have a pthread_sleep() function. We
// do it the portable way, using a timed wait for a condition that we
// will never signal. NOTE: The unistd functions sleep/usleep suspends
// the entire PROCESS, not a signle thread, which is why we can not
// use them to implement glfwSleep.
// Set timeout time, relatvie to current time
gettimeofday( &currenttime, NULL );
dt_sec = (long) time;
dt_usec = (long) ((time - (double)dt_sec) * 1000000.0);
wait.tv_nsec = (currenttime.tv_usec + dt_usec) * 1000L;
if( wait.tv_nsec > 1000000000L )
{
wait.tv_nsec -= 1000000000L;
dt_sec++;
}
wait.tv_sec = currenttime.tv_sec + dt_sec;
// Initialize condition and mutex objects
pthread_mutex_init( &mutex, NULL );
pthread_cond_init( &cond, NULL );
// Do a timed wait
pthread_mutex_lock( &mutex );
pthread_cond_timedwait( &cond, &mutex, &wait );
pthread_mutex_unlock( &mutex );
// Destroy condition and mutex objects
pthread_mutex_destroy( &mutex );
pthread_cond_destroy( &cond );
#else
// For systems without PTHREAD, use unistd usleep
if( time > 0 )
{
usleep( (unsigned int) (time*1000000) );
}
#endif // _GLFW_HAS_PTHREAD
}
File diff suppressed because it is too large Load Diff
+98
View File
@@ -0,0 +1,98 @@
Changes for 1.5.0:
* New feature: assertions can be safely called in multiple threads
where the pthreads library is available.
* New feature: predicates used inside EXPECT_TRUE() and friends
can now generate custom failure messages.
* New feature: Google Test can now be compiled as a DLL.
* New feature: fused source files are included.
* New feature: prints help when encountering unrecognized Google Test flags.
* Experimental feature: CMake build script (requires CMake 2.6.4+).
* Experimental feature: the Pump script for meta programming.
* double values streamed to an assertion are printed with enough precision
to differentiate any two different values.
* Google Test now works on Solaris and AIX.
* Build and test script improvements.
* Bug fixes and implementation clean-ups.
Potentially breaking changes:
* Stopped supporting VC++ 7.1 with exceptions disabled.
* Dropped support for 'make install'.
Changes for 1.4.0:
* New feature: the event listener API
* New feature: test shuffling
* New feature: the XML report format is closer to junitreport and can
be parsed by Hudson now.
* New feature: when a test runs under Visual Studio, its failures are
integrated in the IDE.
* New feature: /MD(d) versions of VC++ projects.
* New feature: elapsed time for the tests is printed by default.
* New feature: comes with a TR1 tuple implementation such that Boost
is no longer needed for Combine().
* New feature: EXPECT_DEATH_IF_SUPPORTED macro and friends.
* New feature: the Xcode project can now produce static gtest
libraries in addition to a framework.
* Compatibility fixes for Solaris, Cygwin, minGW, Windows Mobile,
Symbian, gcc, and C++Builder.
* Bug fixes and implementation clean-ups.
Changes for 1.3.0:
* New feature: death tests on Windows, Cygwin, and Mac.
* New feature: ability to use Google Test assertions in other testing
frameworks.
* New feature: ability to run disabled test via
--gtest_also_run_disabled_tests.
* New feature: the --help flag for printing the usage.
* New feature: access to Google Test flag values in user code.
* New feature: a script that packs Google Test into one .h and one
.cc file for easy deployment.
* New feature: support for distributing test functions to multiple
machines (requires support from the test runner).
* Bug fixes and implementation clean-ups.
Changes for 1.2.1:
* Compatibility fixes for Linux IA-64 and IBM z/OS.
* Added support for using Boost and other TR1 implementations.
* Changes to the build scripts to support upcoming release of Google C++
Mocking Framework.
* Added Makefile to the distribution package.
* Improved build instructions in README.
Changes for 1.2.0:
* New feature: value-parameterized tests.
* New feature: the ASSERT/EXPECT_(NON)FATAL_FAILURE(_ON_ALL_THREADS)
macros.
* Changed the XML report format to match JUnit/Ant's.
* Added tests to the Xcode project.
* Added scons/SConscript for building with SCons.
* Added src/gtest-all.cc for building Google Test from a single file.
* Fixed compatibility with Solaris and z/OS.
* Enabled running Python tests on systems with python 2.3 installed,
e.g. Mac OS X 10.4.
* Bug fixes.
Changes for 1.1.0:
* New feature: type-parameterized tests.
* New feature: exception assertions.
* New feature: printing elapsed time of tests.
* Improved the robustness of death tests.
* Added an Xcode project and samples.
* Adjusted the output format on Windows to be understandable by Visual Studio.
* Minor bug fixes.
Changes for 1.0.1:
* Added project files for Visual Studio 7.1.
* Fixed issues with compiling on Mac OS X.
* Fixed issues with compiling on Cygwin.
Changes for 1.0.0:
* Initial Open Source release of Google Test
+15
View File
@@ -0,0 +1,15 @@
add_library(gtest
fused-src/gtest/gtest_main.cc
fused-src/gtest/gtest-all.cc
fused-src/gtest/gtest.h)
set_target_properties(gtest
PROPERTIES FOLDER "extern")
# gtest library requires linking with thread's library
find_package(Threads)
target_link_libraries(gtest
${CMAKE_THREAD_LIBS_INIT})
target_include_directories(gtest PUBLIC
$<BUILD_INTERFACE:${PROJECT_SOURCE_DIR}/extern/gtest/fused-src>)
+36
View File
@@ -0,0 +1,36 @@
# This file contains a list of people who've made non-trivial
# contribution to the Google C++ Testing Framework project. People
# who commit code to the project are encouraged to add their names
# here. Please keep the list sorted by first names.
Ajay Joshi <jaj@google.com>
Balázs Dán <balazs.dan@gmail.com>
Bharat Mediratta <bharat@menalto.com>
Chandler Carruth <chandlerc@google.com>
Chris Prince <cprince@google.com>
Chris Taylor <taylorc@google.com>
Dan Egnor <egnor@google.com>
Eric Roman <eroman@chromium.org>
Hady Zalek <hady.zalek@gmail.com>
Jeffrey Yasskin <jyasskin@google.com>
Jói Sigurðsson <joi@google.com>
Keir Mierle <mierle@gmail.com>
Keith Ray <keith.ray@gmail.com>
Kenton Varda <kenton@google.com>
Manuel Klimek <klimek@google.com>
Markus Heule <markus.heule@gmail.com>
Mika Raento <mikie@iki.fi>
Miklós Fazekas <mfazekas@szemafor.com>
Patrick Hanna <phanna@google.com>
Patrick Riley <pfr@google.com>
Peter Kaminski <piotrk@google.com>
Preston Jackson <preston.a.jackson@gmail.com>
Rainer Klaffenboeck <rainer.klaffenboeck@dynatrace.com>
Russ Cox <rsc@google.com>
Russ Rufer <russ@pentad.com>
Sean Mcafee <eefacm@gmail.com>
Sigurður Ásgeirsson <siggi@google.com>
Tracy Bialik <tracy@pentad.com>
Vadim Berman <vadimb@google.com>
Vlad Losev <vladl@google.com>
Zhanyong Wan <wan@google.com>
+28
View File
@@ -0,0 +1,28 @@
Copyright 2008, Google Inc.
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 Google Inc. 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 THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"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 THE COPYRIGHT
OWNER OR CONTRIBUTORS 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.
+417
View File
@@ -0,0 +1,417 @@
Google C++ Testing Framework
============================
http://code.google.com/p/googletest/
Overview
--------
Google's framework for writing C++ tests on a variety of platforms
(Linux, Mac OS X, Windows, Windows CE, Symbian, etc). Based on the
xUnit architecture. Supports automatic test discovery, a rich set of
assertions, user-defined assertions, death tests, fatal and non-fatal
failures, various options for running the tests, and XML test report
generation.
Please see the project page above for more information as well as the
mailing list for questions, discussions, and development. There is
also an IRC channel on OFTC (irc.oftc.net) #gtest available. Please
join us!
Requirements for End Users
--------------------------
Google Test is designed to have fairly minimal requirements to build
and use with your projects, but there are some. Currently, we support
Linux, Windows, Mac OS X, and Cygwin. We will also make our best
effort to support other platforms (e.g. Solaris, AIX, and z/OS).
However, since core members of the Google Test project have no access
to these platforms, Google Test may have outstanding issues there. If
you notice any problems on your platform, please notify
googletestframework@googlegroups.com. Patches for fixing them are
even more welcome!
### Linux Requirements ###
These are the base requirements to build and use Google Test from a source
package (as described below):
* GNU-compatible Make or gmake
* POSIX-standard shell
* POSIX(-2) Regular Expressions (regex.h)
* A C++98-standard-compliant compiler
### Windows Requirements ###
* Microsoft Visual C++ 7.1 or newer
### Cygwin Requirements ###
* Cygwin 1.5.25-14 or newer
### Mac OS X Requirements ###
* Mac OS X 10.4 Tiger or newer
* Developer Tools Installed
Also, you'll need CMake 2.6.4 or higher if you want to build the
samples using the provided CMake script, regardless of the platform.
Requirements for Contributors
-----------------------------
We welcome patches. If you plan to contribute a patch, you need to
build Google Test and its own tests from an SVN checkout (described
below), which has further requirements:
* Python version 2.3 or newer (for running some of the tests and
re-generating certain source files from templates)
* CMake 2.6.4 or newer
Getting the Source
------------------
There are two primary ways of getting Google Test's source code: you
can download a stable source release in your preferred archive format,
or directly check out the source from our Subversion (SVN) repositary.
The SVN checkout requires a few extra steps and some extra software
packages on your system, but lets you track the latest development and
make patches much more easily, so we highly encourage it.
### Source Package ###
Google Test is released in versioned source packages which can be
downloaded from the download page [1]. Several different archive
formats are provided, but the only difference is the tools used to
manipulate them, and the size of the resulting file. Download
whichever you are most comfortable with.
[1] http://code.google.com/p/googletest/downloads/list
Once the package is downloaded, expand it using whichever tools you
prefer for that type. This will result in a new directory with the
name "gtest-X.Y.Z" which contains all of the source code. Here are
some examples on Linux:
tar -xvzf gtest-X.Y.Z.tar.gz
tar -xvjf gtest-X.Y.Z.tar.bz2
unzip gtest-X.Y.Z.zip
### SVN Checkout ###
To check out the main branch (also known as the "trunk") of Google
Test, run the following Subversion command:
svn checkout http://googletest.googlecode.com/svn/trunk/ gtest-svn
Setting up the Build
--------------------
To build Google Test and your tests that use it, you need to tell your
build system where to find its headers and source files. The exact
way to do it depends on which build system you use, and is usually
straightforward.
### Generic Build Instructions ###
Suppose you put Google Test in directory ${GTEST_DIR}. To build it,
create a library build target (or a project as called by Visual Studio
and Xcode) to compile
${GTEST_DIR}/src/gtest-all.cc
with
${GTEST_DIR}/include and ${GTEST_DIR}
in the header search path. Assuming a Linux-like system and gcc,
something like the following will do:
g++ -I${GTEST_DIR}/include -I${GTEST_DIR} -c ${GTEST_DIR}/src/gtest-all.cc
ar -rv libgtest.a gtest-all.o
Next, you should compile your test source file with
${GTEST_DIR}/include in the header search path, and link it with gtest
and any other necessary libraries:
g++ -I${GTEST_DIR}/include path/to/your_test.cc libgtest.a -o your_test
As an example, the make/ directory contains a Makefile that you can
use to build Google Test on systems where GNU make is available
(e.g. Linux, Mac OS X, and Cygwin). It doesn't try to build Google
Test's own tests. Instead, it just builds the Google Test library and
a sample test. You can use it as a starting point for your own build
script.
If the default settings are correct for your environment, the
following commands should succeed:
cd ${GTEST_DIR}/make
make
./sample1_unittest
If you see errors, try to tweak the contents of make/Makefile to make
them go away. There are instructions in make/Makefile on how to do
it.
### Using CMake ###
Google Test comes with a CMake build script (CMakeLists.txt) that can
be used on a wide range of platforms ("C" stands for cross-platofrm.).
If you don't have CMake installed already, you can download it for
free from http://www.cmake.org/.
CMake works by generating native makefiles or build projects that can
be used in the compiler environment of your choice. The typical
workflow starts with:
mkdir mybuild # Create a directory to hold the build output.
cd mybuild
cmake ${GTEST_DIR} # Generate native build scripts.
If you want to build Google Test's samples, you should replace the
last command with
cmake -Dbuild_gtest_samples=ON ${GTEST_DIR}
If you are on a *nix system, you should now see a Makefile in the
current directory. Just type 'make' to build gtest.
If you use Windows and have Vistual Studio installed, a gtest.sln file
and several .vcproj files will be created. You can then build them
using Visual Studio.
On Mac OS X with Xcode installed, a .xcodeproj file will be generated.
### Legacy Build Scripts ###
Before settling on CMake, we have been providing hand-maintained build
projects/scripts for Visual Studio, Xcode, and Autotools. While we
continue to provide them for convenience, they are not actively
maintained any more. We highly recommend that you follow the
instructions in the previous two sections to integrate Google Test
with your existing build system.
If you still need to use the legacy build scripts, here's how:
The msvc\ folder contains two solutions with Visual C++ projects.
Open the gtest.sln or gtest-md.sln file using Visual Studio, and you
are ready to build Google Test the same way you build any Visual
Studio project. Files that have names ending with -md use DLL
versions of Microsoft runtime libraries (the /MD or the /MDd compiler
option). Files without that suffix use static versions of the runtime
libraries (the /MT or the /MTd option). Please note that one must use
the same option to compile both gtest and the test code. If you use
Visual Studio 2005 or above, we recommend the -md version as /MD is
the default for new projects in these versions of Visual Studio.
On Mac OS X, open the gtest.xcodeproj in the xcode/ folder using
Xcode. Build the "gtest" target. The universal binary framework will
end up in your selected build directory (selected in the Xcode
"Preferences..." -> "Building" pane and defaults to xcode/build).
Alternatively, at the command line, enter:
xcodebuild
This will build the "Release" configuration of gtest.framework in your
default build location. See the "xcodebuild" man page for more
information about building different configurations and building in
different locations.
Tweaking Google Test
--------------------
Google Test can be used in diverse environments. The default
configuration may not work (or may not work well) out of the box in
some environments. However, you can easily tweak Google Test by
defining control macros on the compiler command line. Generally,
these macros are named like GTEST_XYZ and you define them to either 1
or 0 to enable or disable a certain feature.
We list the most frequently used macros below. For a complete list,
see file include/gtest/internal/gtest-port.h.
### Choosing a TR1 Tuple Library ###
Some Google Test features require the C++ Technical Report 1 (TR1)
tuple library, which is not yet available with all compilers. The
good news is that Google Test implements a subset of TR1 tuple that's
enough for its own need, and will automatically use this when the
compiler doesn't provide TR1 tuple.
Usually you don't need to care about which tuple library Google Test
uses. However, if your project already uses TR1 tuple, you need to
tell Google Test to use the same TR1 tuple library the rest of your
project uses, or the two tuple implementations will clash. To do
that, add
-DGTEST_USE_OWN_TR1_TUPLE=0
to the compiler flags while compiling Google Test and your tests. If
you want to force Google Test to use its own tuple library, just add
-DGTEST_USE_OWN_TR1_TUPLE=1
to the compiler flags instead.
If you don't want Google Test to use tuple at all, add
-DGTEST_HAS_TR1_TUPLE=0
and all features using tuple will be disabled.
### Multi-threaded Tests ###
Google Test is thread-safe where the pthread library is available.
After #include <gtest/gtest.h>, you can check the GTEST_IS_THREADSAFE
macro to see whether this is the case (yes if the macro is #defined to
1, no if it's undefined.).
If Google Test doesn't correctly detect whether pthread is available
in your environment, you can force it with
-DGTEST_HAS_PTHREAD=1
or
-DGTEST_HAS_PTHREAD=0
When Google Test uses pthread, you may need to add flags to your
compiler and/or linker to select the pthread library, or you'll get
link errors. If you use the CMake script or the deprecated Autotools
script, this is taken care of for you. If you use your own build
script, you'll need to read your compiler and linker's manual to
figure out what flags to add.
### As a Shared Library (DLL) ###
Google Test is compact, so most users can build and link it as a
static library for the simplicity. You can choose to use Google Test
as a shared library (known as a DLL on Windows) if you prefer.
To compile gtest as a shared library, add
-DGTEST_CREATE_SHARED_LIBRARY=1
to the compiler flags. You'll also need to tell the linker to produce
a shared library instead - consult your linker's manual for how to do
it.
To compile your tests that use the gtest shared library, add
-DGTEST_LINKED_AS_SHARED_LIBRARY=1
to the compiler flags.
### Avoiding Macro Name Clashes ###
In C++, macros don't obey namespaces. Therefore two libraries that
both define a macro of the same name will clash if you #include both
definitions. In case a Google Test macro clashes with another
library, you can force Google Test to rename its macro to avoid the
conflict.
Specifically, if both Google Test and some other code define macro
FOO, you can add
-DGTEST_DONT_DEFINE_FOO=1
to the compiler flags to tell Google Test to change the macro's name
from FOO to GTEST_FOO. Currently FOO can be FAIL, SUCCEED, or TEST.
For example, with -DGTEST_DONT_DEFINE_TEST=1, you'll need to write
GTEST_TEST(SomeTest, DoesThis) { ... }
instead of
TEST(SomeTest, DoesThis) { ... }
in order to define a test.
Upgrating from an Earlier Version
---------------------------------
We strive to keep Google Test releases backward compatible.
Sometimes, though, we have to make some breaking changes for the
users' long-term benefits. This section describes what you'll need to
do if you are upgrading from an earlier version of Google Test.
### Upgrading from 1.3.0 or Earlier ###
You may need to explicitly enable or disable Google Test's own TR1
tuple library. See the instructions in section "Choosing a TR1 Tuple
Library".
### Upgrading from 1.4.0 or Earlier ###
The Autotools build script (configure + make) is no longer officially
supportted. You are encouraged to migrate to your own build system or
use CMake. If you still need to use Autotools, you can find
instructions in the README file from Google Test 1.4.0.
On platforms where the pthread library is available, Google Test uses
it in order to be thread-safe. See the "Multi-threaded Tests" section
for what this means to your build script.
If you use Microsoft Visual C++ 7.1 with exceptions disabled, Google
Test will no longer compile. This should affect very few people, as a
large portion of STL (including <string>) doesn't compile in this mode
anyway. We decided to stop supporting it in order to greatly simplify
Google Test's implementation.
Developing Google Test
----------------------
This section discusses how to make your own changes to Google Test.
### Testing Google Test Itself ###
To make sure your changes work as intended and don't break existing
functionality, you'll want to compile and run Google Test's own tests.
For that you can use CMake:
mkdir mybuild
cd mybuild
cmake -Dbuild_all_gtest_tests=ON ${GTEST_DIR}
Make sure you have Python installed, as some of Google Test's tests
are written in Python. If the cmake command complains about not being
able to find Python ("Could NOT find PythonInterp (missing:
PYTHON_EXECUTABLE)"), try telling it explicitly where your Python
executable can be found:
cmake -DPYTHON_EXECUTABLE=path/to/python -Dbuild_all_gtest_tests=ON \
${GTEST_DIR}
Next, you can build Google Test and all of its own tests. On *nix,
this is usually done by 'make'. To run the tests, do
make test
All tests should pass.
### Regenerating Source Files ###
Some of Google Test's source files are generated from templates (not
in the C++ sense) using a script. A template file is named FOO.pump,
where FOO is the name of the file it will generate. For example, the
file include/gtest/internal/gtest-type-util.h.pump is used to generate
gtest-type-util.h in the same directory.
Normally you don't need to worry about regenerating the source files,
unless you need to modify them. In that case, you should modify the
corresponding .pump files instead and run the pump.py Python script to
regenerate them. You can find pump.py in the scripts/ directory.
Read the Pump manual [2] for how to use it.
[2] http://code.google.com/p/googletest/wiki/PumpManual
### Contributing a Patch ###
We welcome patches. Please read the Google Test developer's guide [3]
for how you can contribute. In particular, make sure you have signed
the Contributor License Agreement, or we won't be able to accept the
patch.
[3] http://code.google.com/p/googletest/wiki/GoogleTestDevGuide
Happy testing!
+20
View File
@@ -0,0 +1,20 @@
URL: http://code.google.com/p/googletest/
Version: 1.7.0
(Downloaded gtest-1.7.0.zip
from https://github.com/google/googletest)
License: BSD
Note: gtest was developed by Google, and Google holds the
copyright. Any contributions accepted from non-Google employees were
accepted under a Google contributor license agreement
(http://code.google.com/legal/individual-cla-v1.0.html or
http://code.google.com/legal/corporate-cla-v1.0.html)
License File: COPYING (but see above)
Description: gtest is an open-source unit test framework.
Local Modifications:
- Extracted include and source files from gtest package.
- Striped from unsued files and only kept the fused files.
- Added CMakeLists.txt build file.
- Removed printf trace for gtest main.
- Disables tr1/tuple with GTEST_HAS_TR1_TUPLE macro definition.
- Fixes build warnings.
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
@@ -0,0 +1,38 @@
// Copyright 2006, Google Inc.
// 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 Google Inc. 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 THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "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 THE COPYRIGHT
// OWNER OR CONTRIBUTORS 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.
#include <stdio.h>
#include "gtest/gtest.h"
GTEST_API_ int main(int argc, char **argv) {
printf("Running main() from gtest_main.cc\n");
testing::InitGoogleTest(&argc, argv);
return RUN_ALL_TESTS();
}
+13
View File
@@ -0,0 +1,13 @@
add_library(json
dist/jsoncpp.cpp
dist/json/json.h
dist/json/json-forwards.h)
set_target_properties(json
PROPERTIES FOLDER "extern")
set_target_properties(json
PROPERTIES COMPILE_OPTIONS $<$<CXX_COMPILER_ID:MSVC>:/wd4702>)
target_include_directories(json PUBLIC
$<BUILD_INTERFACE:${PROJECT_SOURCE_DIR}/extern/jsoncpp/dist>)
+55
View File
@@ -0,0 +1,55 @@
The JsonCpp library's source code, including accompanying documentation,
tests and demonstration applications, are licensed under the following
conditions...
The author (Baptiste Lepilleur) explicitly disclaims copyright in all
jurisdictions which recognize such a disclaimer. In such jurisdictions,
this software is released into the Public Domain.
In jurisdictions which do not recognize Public Domain property (e.g. Germany as of
2010), this software is Copyright (c) 2007-2010 by Baptiste Lepilleur, and is
released under the terms of the MIT License (see below).
In jurisdictions which recognize Public Domain property, the user of this
software may choose to accept it either as 1) Public Domain, 2) under the
conditions of the MIT License (see below), or 3) under the terms of dual
Public Domain/MIT License conditions described here, as they choose.
The MIT License is about as close to Public Domain as a license can get, and is
described in clear, concise terms at:
http://en.wikipedia.org/wiki/MIT_License
The full text of the MIT License follows:
========================================================================
Copyright (c) 2007-2010 Baptiste Lepilleur
Permission is hereby granted, free of charge, to any person
obtaining a copy of this software and associated documentation
files (the "Software"), to deal in the Software without
restriction, including without limitation the rights to use, copy,
modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is
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 Software.
THE SOFTWARE IS 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 SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
========================================================================
(END LICENSE TEXT)
The MIT license is compatible with both the GPL and commercial
software, affording one all of the rights of Public Domain with the
minor nuisance of being required to keep the above copyright notice
and license text in the source code. Note also that by accepting the
Public Domain "license" you can re-license your copy using whatever
license you like.
+214
View File
@@ -0,0 +1,214 @@
Introduction
------------
[JSON][json-org] is a lightweight data-interchange format. It can represent
numbers, strings, ordered sequences of values, and collections of name/value
pairs.
[json-org]: http://json.org/
[JsonCpp][] is a C++ library that allows manipulating JSON values, including
serialization and deserialization to and from strings. It can also preserve
existing comment in unserialization/serialization steps, making it a convenient
format to store user input files.
[JsonCpp]: http://open-source-parsers.github.io/jsoncpp-docs/doxygen/index.html
## A note on backward-compatibility
* `1.y.z` is built with C++11.
* `0.y.z` can be used with older compilers.
* Major versions maintain binary-compatibility.
# Using JsonCpp in your project
-----------------------------
The recommended approach to integrating JsonCpp in your project is to include
the [amalgamated source](#generating-amalgamated-source-and-header) (a single
`.cpp` file and two `.h` files) in your project, and compile and build as you
would any other source file. This ensures consistency of compilation flags and
ABI compatibility, issues which arise when building shared or static
libraries. See the next section for instructions.
The `include/` should be added to your compiler include path. Jsoncpp headers
should be included as follow:
#include <json/json.h>
If JsonCpp was built as a dynamic library on Windows, then your project needs to
define the macro `JSON_DLL`.
Generating amalgamated source and header
----------------------------------------
JsonCpp is provided with a script to generate a single header and a single
source file to ease inclusion into an existing project. The amalgamated source
can be generated at any time by running the following command from the
top-directory (this requires Python 2.6):
python amalgamate.py
It is possible to specify header name. See the `-h` option for detail.
By default, the following files are generated:
* `dist/jsoncpp.cpp`: source file that needs to be added to your project.
* `dist/json/json.h`: corresponding header file for use in your project. It is
equivalent to including `json/json.h` in non-amalgamated source. This header
only depends on standard headers.
* `dist/json/json-forwards.h`: header that provides forward declaration of all
JsonCpp types.
The amalgamated sources are generated by concatenating JsonCpp source in the
correct order and defining the macro `JSON_IS_AMALGAMATION` to prevent inclusion
of other headers.
# Contributing to JsonCpp
Building and testing with CMake
-------------------------------
[CMake][] is a C++ Makefiles/Solution generator. It is usually available on most
Linux system as package. On Ubuntu:
sudo apt-get install cmake
[CMake]: http://www.cmake.org
Note that Python is also required to run the JSON reader/writer tests. If
missing, the build will skip running those tests.
When running CMake, a few parameters are required:
* a build directory where the makefiles/solution are generated. It is also used
to store objects, libraries and executables files.
* the generator to use: makefiles or Visual Studio solution? What version or
Visual Studio, 32 or 64 bits solution?
Steps for generating solution/makefiles using `cmake-gui`:
* Make "source code" point to the source directory.
* Make "where to build the binary" point to the directory to use for the build.
* Click on the "Grouped" check box.
* Review JsonCpp build options (tick `BUILD_SHARED_LIBS` to build as a
dynamic library).
* Click the configure button at the bottom, then the generate button.
* The generated solution/makefiles can be found in the binary directory.
Alternatively, from the command-line on Unix in the source directory:
mkdir -p build/debug
cd build/debug
cmake -DCMAKE_BUILD_TYPE=debug -DBUILD_STATIC_LIBS=ON -DBUILD_SHARED_LIBS=OFF -DARCHIVE_INSTALL_DIR=. -G "Unix Makefiles" ../..
make
Running `cmake -h` will display the list of available generators (passed using
the `-G` option).
By default CMake hides compilation commands. This can be modified by specifying
`-DCMAKE_VERBOSE_MAKEFILE=true` when generating makefiles.
Building and testing with SCons
-------------------------------
**Note:** The SCons-based build system is deprecated. Please use CMake; see the
section above.
JsonCpp can use [Scons][] as a build system. Note that SCons requires Python to
be installed.
[SCons]: http://www.scons.org/
Invoke SCons as follows:
scons platform=$PLATFORM [TARGET]
where `$PLATFORM` may be one of:
* `suncc`: Sun C++ (Solaris)
* `vacpp`: Visual Age C++ (AIX)
* `mingw`
* `msvc6`: Microsoft Visual Studio 6 service pack 5-6
* `msvc70`: Microsoft Visual Studio 2002
* `msvc71`: Microsoft Visual Studio 2003
* `msvc80`: Microsoft Visual Studio 2005
* `msvc90`: Microsoft Visual Studio 2008
* `linux-gcc`: Gnu C++ (linux, also reported to work for Mac OS X)
If you are building with Microsoft Visual Studio 2008, you need to set up the
environment by running `vcvars32.bat` (e.g. MSVC 2008 command prompt) before
running SCons.
## Running the tests manually
You need to run tests manually only if you are troubleshooting an issue.
In the instructions below, replace `path/to/jsontest` with the path of the
`jsontest` executable that was compiled on your platform.
cd test
# This will run the Reader/Writer tests
python runjsontests.py path/to/jsontest
# This will run the Reader/Writer tests, using JSONChecker test suite
# (http://www.json.org/JSON_checker/).
# Notes: not all tests pass: JsonCpp is too lenient (for example,
# it allows an integer to start with '0'). The goal is to improve
# strict mode parsing to get all tests to pass.
python runjsontests.py --with-json-checker path/to/jsontest
# This will run the unit tests (mostly Value)
python rununittests.py path/to/test_lib_json
# You can run the tests using valgrind:
python rununittests.py --valgrind path/to/test_lib_json
## Running the tests using scons
Note that tests can be run using SCons using the `check` target:
scons platform=$PLATFORM check
Building the documentation
--------------------------
Run the Python script `doxybuild.py` from the top directory:
python doxybuild.py --doxygen=$(which doxygen) --open --with-dot
See `doxybuild.py --help` for options.
Adding a reader/writer test
---------------------------
To add a test, you need to create two files in test/data:
* a `TESTNAME.json` file, that contains the input document in JSON format.
* a `TESTNAME.expected` file, that contains a flatened representation of the
input document.
The `TESTNAME.expected` file format is as follows:
* each line represents a JSON element of the element tree represented by the
input document.
* each line has two parts: the path to access the element separated from the
element value by `=`. Array and object values are always empty (i.e.
represented by either `[]` or `{}`).
* element path: `.` represents the root element, and is used to separate object
members. `[N]` is used to specify the value of an array element at index `N`.
See the examples `test_complex_01.json` and `test_complex_01.expected` to better
understand element paths.
Understanding reader/writer test output
---------------------------------------
When a test is run, output files are generated beside the input test files.
Below is a short description of the content of each file:
* `test_complex_01.json`: input JSON document.
* `test_complex_01.expected`: flattened JSON element tree used to check if
parsing was corrected.
* `test_complex_01.actual`: flattened JSON element tree produced by `jsontest`
from reading `test_complex_01.json`.
* `test_complex_01.rewrite`: JSON document written by `jsontest` using the
`Json::Value` parsed from `test_complex_01.json` and serialized using
`Json::StyledWritter`.
* `test_complex_01.actual-rewrite`: flattened JSON element tree produced by
`jsontest` from reading `test_complex_01.rewrite`.
* `test_complex_01.process-output`: `jsontest` output, typically useful for
understanding parsing errors.
License
-------
See the `LICENSE` file for details. In summary, JsonCpp is licensed under the
MIT license, or public domain if desired and recognized in your jurisdiction.
+12
View File
@@ -0,0 +1,12 @@
URL: https://github.com/open-source-parsers/jsoncpp
Version: 0.y.z
License: PUBLIC DOMAIN
License File: LICENSE
Description: A C++ library for interacting with JSON.
Local Modifications:
- Extracted amalgamated source files from jsoncpp package.
- Creates a specific CMakeLists.txt
- Fixes MSVC warning C4512: 'Json::Exception' : assignment operator could not be generated.
- Modifies Value::asCString() to return an empty string instead of NULL when string length is 0.
- Sorts members by insertion time, in order to dump them in a defined order.
@@ -0,0 +1,265 @@
/// Json-cpp amalgated forward header (http://jsoncpp.sourceforge.net/).
/// It is intended to be used with #include "json/json-forwards.h"
/// This header provides forward declaration for all JsonCpp types.
// //////////////////////////////////////////////////////////////////////
// Beginning of content of file: LICENSE
// //////////////////////////////////////////////////////////////////////
/*
The JsonCpp library's source code, including accompanying documentation,
tests and demonstration applications, are licensed under the following
conditions...
The author (Baptiste Lepilleur) explicitly disclaims copyright in all
jurisdictions which recognize such a disclaimer. In such jurisdictions,
this software is released into the Public Domain.
In jurisdictions which do not recognize Public Domain property (e.g. Germany as of
2010), this software is Copyright (c) 2007-2010 by Baptiste Lepilleur, and is
released under the terms of the MIT License (see below).
In jurisdictions which recognize Public Domain property, the user of this
software may choose to accept it either as 1) Public Domain, 2) under the
conditions of the MIT License (see below), or 3) under the terms of dual
Public Domain/MIT License conditions described here, as they choose.
The MIT License is about as close to Public Domain as a license can get, and is
described in clear, concise terms at:
http://en.wikipedia.org/wiki/MIT_License
The full text of the MIT License follows:
========================================================================
Copyright (c) 2007-2010 Baptiste Lepilleur
Permission is hereby granted, free of charge, to any person
obtaining a copy of this software and associated documentation
files (the "Software"), to deal in the Software without
restriction, including without limitation the rights to use, copy,
modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is
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 Software.
THE SOFTWARE IS 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 SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
========================================================================
(END LICENSE TEXT)
The MIT license is compatible with both the GPL and commercial
software, affording one all of the rights of Public Domain with the
minor nuisance of being required to keep the above copyright notice
and license text in the source code. Note also that by accepting the
Public Domain "license" you can re-license your copy using whatever
license you like.
*/
// //////////////////////////////////////////////////////////////////////
// End of content of file: LICENSE
// //////////////////////////////////////////////////////////////////////
#ifndef JSON_FORWARD_AMALGATED_H_INCLUDED
# define JSON_FORWARD_AMALGATED_H_INCLUDED
/// If defined, indicates that the source file is amalgated
/// to prevent private header inclusion.
#define JSON_IS_AMALGAMATION
// //////////////////////////////////////////////////////////////////////
// Beginning of content of file: include/json/config.h
// //////////////////////////////////////////////////////////////////////
// Copyright 2007-2010 Baptiste Lepilleur
// Distributed under MIT license, or public domain if desired and
// recognized in your jurisdiction.
// See file LICENSE for detail or copy at http://jsoncpp.sourceforge.net/LICENSE
#ifndef JSON_CONFIG_H_INCLUDED
#define JSON_CONFIG_H_INCLUDED
/// If defined, indicates that json library is embedded in CppTL library.
//# define JSON_IN_CPPTL 1
/// If defined, indicates that json may leverage CppTL library
//# define JSON_USE_CPPTL 1
/// If defined, indicates that cpptl vector based map should be used instead of
/// std::map
/// as Value container.
//# define JSON_USE_CPPTL_SMALLMAP 1
// If non-zero, the library uses exceptions to report bad input instead of C
// assertion macros. The default is to use exceptions.
#ifndef JSON_USE_EXCEPTION
#define JSON_USE_EXCEPTION 1
#endif
/// If defined, indicates that the source file is amalgated
/// to prevent private header inclusion.
/// Remarks: it is automatically defined in the generated amalgated header.
// #define JSON_IS_AMALGAMATION
#ifdef JSON_IN_CPPTL
#include <cpptl/config.h>
#ifndef JSON_USE_CPPTL
#define JSON_USE_CPPTL 1
#endif
#endif
#ifdef JSON_IN_CPPTL
#define JSON_API CPPTL_API
#elif defined(JSON_DLL_BUILD)
#if defined(_MSC_VER)
#define JSON_API __declspec(dllexport)
#define JSONCPP_DISABLE_DLL_INTERFACE_WARNING
#endif // if defined(_MSC_VER)
#elif defined(JSON_DLL)
#if defined(_MSC_VER)
#define JSON_API __declspec(dllimport)
#define JSONCPP_DISABLE_DLL_INTERFACE_WARNING
#endif // if defined(_MSC_VER)
#endif // ifdef JSON_IN_CPPTL
#if !defined(JSON_API)
#define JSON_API
#endif
#if !defined(JSON_HAS_UNIQUE_PTR)
#if __cplusplus >= 201103L
#define JSON_HAS_UNIQUE_PTR (1)
#elif _MSC_VER >= 1600
#define JSON_HAS_UNIQUE_PTR (1)
#else
#define JSON_HAS_UNIQUE_PTR (0)
#endif
#endif
// If JSON_NO_INT64 is defined, then Json only support C++ "int" type for
// integer
// Storages, and 64 bits integer support is disabled.
// #define JSON_NO_INT64 1
#if defined(_MSC_VER) && _MSC_VER <= 1200 // MSVC 6
// Microsoft Visual Studio 6 only support conversion from __int64 to double
// (no conversion from unsigned __int64).
#define JSON_USE_INT64_DOUBLE_CONVERSION 1
// Disable warning 4786 for VS6 caused by STL (identifier was truncated to '255'
// characters in the debug information)
// All projects I've ever seen with VS6 were using this globally (not bothering
// with pragma push/pop).
#pragma warning(disable : 4786)
#endif // if defined(_MSC_VER) && _MSC_VER < 1200 // MSVC 6
#if defined(_MSC_VER) && _MSC_VER >= 1500 // MSVC 2008
/// Indicates that the following function is deprecated.
#define JSONCPP_DEPRECATED(message) __declspec(deprecated(message))
#elif defined(__clang__) && defined(__has_feature)
#if __has_feature(attribute_deprecated_with_message)
#define JSONCPP_DEPRECATED(message) __attribute__ ((deprecated(message)))
#endif
#elif defined(__GNUC__) && (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 5))
#define JSONCPP_DEPRECATED(message) __attribute__ ((deprecated(message)))
#elif defined(__GNUC__) && (__GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ >= 1))
#define JSONCPP_DEPRECATED(message) __attribute__((__deprecated__))
#endif
#if !defined(JSONCPP_DEPRECATED)
#define JSONCPP_DEPRECATED(message)
#endif // if !defined(JSONCPP_DEPRECATED)
namespace Json {
typedef int Int;
typedef unsigned int UInt;
#if defined(JSON_NO_INT64)
typedef int LargestInt;
typedef unsigned int LargestUInt;
#undef JSON_HAS_INT64
#else // if defined(JSON_NO_INT64)
// For Microsoft Visual use specific types as long long is not supported
#if defined(_MSC_VER) // Microsoft Visual Studio
typedef __int64 Int64;
typedef unsigned __int64 UInt64;
#else // if defined(_MSC_VER) // Other platforms, use long long
typedef long long int Int64;
typedef unsigned long long int UInt64;
#endif // if defined(_MSC_VER)
typedef Int64 LargestInt;
typedef UInt64 LargestUInt;
#define JSON_HAS_INT64
#endif // if defined(JSON_NO_INT64)
} // end namespace Json
#endif // JSON_CONFIG_H_INCLUDED
// //////////////////////////////////////////////////////////////////////
// End of content of file: include/json/config.h
// //////////////////////////////////////////////////////////////////////
// //////////////////////////////////////////////////////////////////////
// Beginning of content of file: include/json/forwards.h
// //////////////////////////////////////////////////////////////////////
// Copyright 2007-2010 Baptiste Lepilleur
// Distributed under MIT license, or public domain if desired and
// recognized in your jurisdiction.
// See file LICENSE for detail or copy at http://jsoncpp.sourceforge.net/LICENSE
#ifndef JSON_FORWARDS_H_INCLUDED
#define JSON_FORWARDS_H_INCLUDED
#if !defined(JSON_IS_AMALGAMATION)
#include "config.h"
#endif // if !defined(JSON_IS_AMALGAMATION)
namespace Json {
// writer.h
class FastWriter;
class StyledWriter;
// reader.h
class Reader;
// features.h
class Features;
// value.h
typedef unsigned int ArrayIndex;
class StaticString;
class Path;
class PathArgument;
class Value;
class ValueIteratorBase;
class ValueIterator;
class ValueConstIterator;
} // namespace Json
#endif // JSON_FORWARDS_H_INCLUDED
// //////////////////////////////////////////////////////////////////////
// End of content of file: include/json/forwards.h
// //////////////////////////////////////////////////////////////////////
#endif //ifndef JSON_FORWARD_AMALGATED_H_INCLUDED
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
+33
View File
@@ -0,0 +1,33 @@
# load_from_file
add_executable(load_from_file
load_from_file.cc)
target_link_libraries(load_from_file
ozz_animation)
set_target_properties(load_from_file
PROPERTIES FOLDER "howtos")
add_test(NAME load_from_file COMMAND load_from_file "${ozz_media_directory}/bin/pab_skeleton.ozz")
add_test(NAME load_from_file_no_arg COMMAND load_from_file)
set_tests_properties(load_from_file_no_arg PROPERTIES WILL_FAIL true)
add_test(NAME load_from_file_bad_arg COMMAND load_from_file "${ozz_media_directory}/bin/doesn_t_exist.ozz")
set_tests_properties(load_from_file_bad_arg PROPERTIES WILL_FAIL true)
# custom_skeleton_importer
add_executable(custom_skeleton_importer
custom_skeleton_importer.cc)
target_link_libraries(custom_skeleton_importer
ozz_animation_offline)
set_target_properties(custom_skeleton_importer
PROPERTIES FOLDER "howtos")
add_test(NAME custom_skeleton_importer COMMAND custom_skeleton_importer)
# custom_animation_importer
add_executable(custom_animation_importer
custom_animation_importer.cc)
target_link_libraries(custom_animation_importer
ozz_animation_offline)
set_target_properties(custom_animation_importer
PROPERTIES FOLDER "howtos")
add_test(NAME custom_animation_importer COMMAND custom_animation_importer)
@@ -0,0 +1,118 @@
//----------------------------------------------------------------------------//
// //
// ozz-animation is hosted at http://github.com/guillaumeblanc/ozz-animation //
// and distributed under the MIT License (MIT). //
// //
// Copyright (c) Guillaume Blanc //
// //
// Permission is hereby granted, free of charge, to any person obtaining a //
// copy of this software and associated documentation files (the "Software"), //
// to deal in the Software without restriction, including without limitation //
// the rights to use, copy, modify, merge, publish, distribute, sublicense, //
// and/or sell copies of the Software, and to permit persons to whom the //
// Software is 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 Software. //
// //
// THE SOFTWARE IS 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 SOFTWARE OR THE USE OR OTHER //
// DEALINGS IN THE SOFTWARE. //
// //
//----------------------------------------------------------------------------//
#include "ozz/animation/offline/animation_builder.h"
#include "ozz/animation/offline/raw_animation.h"
#include "ozz/animation/runtime/animation.h"
#include <cstdlib>
// Code for ozz-animation HowTo: "How to write a custon animation importer?"
int main(int argc, char const* argv[]) {
(void)argc;
(void)argv;
//////////////////////////////////////////////////////////////////////////////
// The first section builds a RawAnimation from custom data.
//////////////////////////////////////////////////////////////////////////////
// Creates a RawAnimation.
ozz::animation::offline::RawAnimation raw_animation;
// Sets animation duration (to 1.4s).
// All the animation keyframes times must be within range [0, duration].
raw_animation.duration = 1.4f;
// Creates 3 animation tracks.
// There should be as much tracks as there are joints in the skeleton that
// this animation targets.
raw_animation.tracks.resize(3);
// Fills each track with keyframes, in joint local-space.
// Tracks should be ordered in the same order as joints in the
// ozz::animation::Skeleton. Joint's names can be used to find joint's
// index in the skeleton.
// Fills 1st track with 2 translation keyframes.
{
// Create a keyframe, at t=0, with a translation value.
const ozz::animation::offline::RawAnimation::TranslationKey key0 = {
0.f, ozz::math::Float3(0.f, 4.6f, 0.f)};
raw_animation.tracks[0].translations.push_back(key0);
// Create a new keyframe, at t=0.93 (must be less than duration), with a
// translation value.
const ozz::animation::offline::RawAnimation::TranslationKey key1 = {
.93f, ozz::math::Float3(0.f, 9.9f, 0.f)};
raw_animation.tracks[0].translations.push_back(key1);
}
// Fills 1st track with a rotation keyframe. It's not mandatory to have the
// same number of keyframes for translation, rotations and scales.
{
// Create a keyframe, at t=.46, with a quaternion value.
const ozz::animation::offline::RawAnimation::RotationKey key0 = {
.46f, ozz::math::Quaternion(0.f, 1.f, 0.f, 0.f)};
raw_animation.tracks[0].rotations.push_back(key0);
}
// For this example, don't fill scale with any key. The default value will be
// identity, which is ozz::math::Float3(1.f, 1.f, 1.f) for scale.
//...and so on with all other tracks...
// Test for animation validity. These are the errors that could invalidate
// an animation:
// 1. Animation duration is less than 0.
// 2. Keyframes' are not sorted in a strict ascending order.
// 3. Keyframes' are not within [0, duration] range.
if (!raw_animation.Validate()) {
return EXIT_FAILURE;
}
//////////////////////////////////////////////////////////////////////////////
// This final section converts the RawAnimation to a runtime Animation.
//////////////////////////////////////////////////////////////////////////////
// Creates a AnimationBuilder instance.
ozz::animation::offline::AnimationBuilder builder;
// Executes the builder on the previously prepared RawAnimation, which returns
// a new runtime animation instance.
// This operation will fail and return an empty unique_ptr if the RawAnimation
// isn't valid.
ozz::unique_ptr<ozz::animation::Animation> animation = builder(raw_animation);
// ...use the animation as you want...
return EXIT_SUCCESS;
}
@@ -0,0 +1,104 @@
//----------------------------------------------------------------------------//
// //
// ozz-animation is hosted at http://github.com/guillaumeblanc/ozz-animation //
// and distributed under the MIT License (MIT). //
// //
// Copyright (c) Guillaume Blanc //
// //
// Permission is hereby granted, free of charge, to any person obtaining a //
// copy of this software and associated documentation files (the "Software"), //
// to deal in the Software without restriction, including without limitation //
// the rights to use, copy, modify, merge, publish, distribute, sublicense, //
// and/or sell copies of the Software, and to permit persons to whom the //
// Software is 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 Software. //
// //
// THE SOFTWARE IS 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 SOFTWARE OR THE USE OR OTHER //
// DEALINGS IN THE SOFTWARE. //
// //
//----------------------------------------------------------------------------//
#include "ozz/animation/offline/raw_skeleton.h"
#include "ozz/animation/offline/skeleton_builder.h"
#include "ozz/animation/runtime/skeleton.h"
#include <cstdlib>
// Code for ozz-animation HowTo: "How to write a custon skeleton importer?"
int main(int argc, char const* argv[]) {
(void)argc;
(void)argv;
//////////////////////////////////////////////////////////////////////////////
// The first section builds a RawSkeleton from custom data.
//////////////////////////////////////////////////////////////////////////////
// Creates a RawSkeleton.
ozz::animation::offline::RawSkeleton raw_skeleton;
// Creates the root joint.
raw_skeleton.roots.resize(1);
ozz::animation::offline::RawSkeleton::Joint& root = raw_skeleton.roots[0];
// Setup root joints name.
root.name = "root";
// Setup root joints bind-pose/rest transformation, in joint local-space.
// This is the default skeleton posture (most of the time a T-pose). It's
// used as a fallback when there's no animation for a joint.
root.transform.translation = ozz::math::Float3(0.f, 1.f, 0.f);
root.transform.rotation = ozz::math::Quaternion(0.f, 0.f, 0.f, 1.f);
root.transform.scale = ozz::math::Float3(1.f, 1.f, 1.f);
// Now adds 2 children to the root.
root.children.resize(2);
// Setups the 1st child name (left) and transfomation.
ozz::animation::offline::RawSkeleton::Joint& left = root.children[0];
left.name = "left";
left.transform.translation = ozz::math::Float3(1.f, 0.f, 0.f);
left.transform.rotation = ozz::math::Quaternion(0.f, 0.f, 0.f, 1.f);
left.transform.scale = ozz::math::Float3(1.f, 1.f, 1.f);
// Setups the 2nd child name (right) and transfomation.
ozz::animation::offline::RawSkeleton::Joint& right = root.children[1];
right.name = "right";
right.transform.translation = ozz::math::Float3(-1.f, 0.f, 0.f);
right.transform.rotation = ozz::math::Quaternion(0.f, 0.f, 0.f, 1.f);
right.transform.scale = ozz::math::Float3(1.f, 1.f, 1.f);
//...and so on with the whole skeleton hierarchy...
// Test for skeleton validity.
// The main invalidity reason is the number of joints, which must be lower
// than ozz::animation::Skeleton::kMaxJoints.
if (!raw_skeleton.Validate()) {
return EXIT_FAILURE;
}
//////////////////////////////////////////////////////////////////////////////
// This final section converts the RawSkeleton to a runtime Skeleton.
//////////////////////////////////////////////////////////////////////////////
// Creates a SkeletonBuilder instance.
ozz::animation::offline::SkeletonBuilder builder;
// Executes the builder on the previously prepared RawSkeleton, which returns
// a new runtime skeleton instance.
// This operation will fail and return an empty unique_ptr if the RawSkeleton
// isn't valid.
ozz::unique_ptr<ozz::animation::Skeleton> skeleton = builder(raw_skeleton);
// ...use the skeleton as you want...
return EXIT_SUCCESS;
}
+112
View File
@@ -0,0 +1,112 @@
//----------------------------------------------------------------------------//
// //
// ozz-animation is hosted at http://github.com/guillaumeblanc/ozz-animation //
// and distributed under the MIT License (MIT). //
// //
// Copyright (c) Guillaume Blanc //
// //
// Permission is hereby granted, free of charge, to any person obtaining a //
// copy of this software and associated documentation files (the "Software"), //
// to deal in the Software without restriction, including without limitation //
// the rights to use, copy, modify, merge, publish, distribute, sublicense, //
// and/or sell copies of the Software, and to permit persons to whom the //
// Software is 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 Software. //
// //
// THE SOFTWARE IS 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 SOFTWARE OR THE USE OR OTHER //
// DEALINGS IN THE SOFTWARE. //
// //
//----------------------------------------------------------------------------//
#include "ozz/base/log.h"
// Provides files abstraction.
#include "ozz/base/io/stream.h"
// Provides serialization/deserialization mechanism.
#include "ozz/base/io/archive.h"
// Uses the skeleton as an example of object to read.
#include "ozz/animation/runtime/skeleton.h"
#include <cstdlib>
// Code for ozz-animation HowTo: "How to load an object from a file?"
int main(int argc, char const* argv[]) {
(void)argc;
(void)argv;
// First check that an argument was provided. We expect it to be a valid
// filename.
if (argc != 2) {
ozz::log::Err() << "Invalid arguments." << std::endl;
return EXIT_FAILURE;
}
// Stores filename.
const char* filename = argv[1];
{
////////////////////////////////////////////////////////////////////////////
// The first section opens a file.
////////////////////////////////////////////////////////////////////////////
// Now tries to open the file, which was provided as argument.
// A file in ozz is a ozz::io::File, which implements ozz::io::Stream
// interface and complies with std FILE specifications.
// ozz::io::File follows RAII programming idiom, which ensures that the file
// will always be closed (by ozz::io::FileStream destructor).
ozz::io::File file(filename, "rb");
// Checks file status, which can be closed if filename is invalid.
if (!file.opened()) {
ozz::log::Err() << "Cannot open file " << filename << "." << std::endl;
return EXIT_FAILURE;
}
////////////////////////////////////////////////////////////////////////////
// The next section deserializes an object from the file.
////////////////////////////////////////////////////////////////////////////
// Now the file is opened. we can actually read from it. This uses ozz
// archive mechanism.
// The first step is to instantiate an read-capable (ozz::io::IArchive)
// archive object, in opposition to write-capable (ozz::io::OArchive)
// archives.
// Archives take as argument stream objects, which must be valid and opened.
ozz::io::IArchive archive(&file);
// Before actually reading the object from the file, we need to test that
// the archive (at current seek position) contains the object type we
// expect.
// Archives uses a tagging system that allows to mark and detect thetype of
// the next object to deserialize. Here we expect a skeleton, so we test for
// a skeleton tag.
// Tagging is not mandatory for all object types. It's usually only used for
// high level object types (skeletons, animations...), but not low level
// ones (math objects, native types...).
if (!archive.TestTag<ozz::animation::Skeleton>()) {
ozz::log::Err() << "Archive doesn't contain the expected object type."
<< std::endl;
return EXIT_FAILURE;
}
// Now the tag has been validated, the object can be read.
// IArchive uses >> operator to read from the archive to the object.
// Only objects that implement archive specifications can be used there,
// along with all native types. Note that pointers aren't supported.
ozz::animation::Skeleton skeleton;
archive >> skeleton;
// Getting out of this scope will destroy "file" object and close the system
// file.
}
return EXIT_SUCCESS;
}
@@ -0,0 +1,76 @@
//----------------------------------------------------------------------------//
// //
// ozz-animation is hosted at http://github.com/guillaumeblanc/ozz-animation //
// and distributed under the MIT License (MIT). //
// //
// Copyright (c) Guillaume Blanc //
// //
// Permission is hereby granted, free of charge, to any person obtaining a //
// copy of this software and associated documentation files (the "Software"), //
// to deal in the Software without restriction, including without limitation //
// the rights to use, copy, modify, merge, publish, distribute, sublicense, //
// and/or sell copies of the Software, and to permit persons to whom the //
// Software is 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 Software. //
// //
// THE SOFTWARE IS 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 SOFTWARE OR THE USE OR OTHER //
// DEALINGS IN THE SOFTWARE. //
// //
//----------------------------------------------------------------------------//
#ifndef OZZ_OZZ_ANIMATION_OFFLINE_ADDITIVE_ANIMATION_BUILDER_H_
#define OZZ_OZZ_ANIMATION_OFFLINE_ADDITIVE_ANIMATION_BUILDER_H_
#include "ozz/base/platform.h"
#include "ozz/base/span.h"
namespace ozz {
namespace math {
struct Transform;
}
namespace animation {
namespace offline {
// Forward declare offline animation type.
struct RawAnimation;
// Defines the class responsible for building a delta animation from an offline
// raw animation. This is used to create animations compatible with additive
// blending.
class AdditiveAnimationBuilder {
public:
// Initializes the builder.
AdditiveAnimationBuilder();
// Builds delta animation from _input..
// Returns true on success and fills _output_animation with the delta
// version of _input animation.
// *_output must be a valid RawAnimation instance. Uses first frame as
// reference pose Returns false on failure and resets _output to an empty
// animation. See RawAnimation::Validate() for more details about failure
// reasons.
bool operator()(const RawAnimation& _input, RawAnimation* _output) const;
// Builds delta animation from _input..
// Returns true on success and fills _output_animation with the delta
// *_output must be a valid RawAnimation instance.
// version of _input animation.
// *_reference_pose used as the base pose to calculate deltas from
// Returns false on failure and resets _output to an empty animation.
bool operator()(const RawAnimation& _input,
const span<const math::Transform>& _reference_pose,
RawAnimation* _output) const;
};
} // namespace offline
} // namespace animation
} // namespace ozz
#endif // OZZ_OZZ_ANIMATION_OFFLINE_ADDITIVE_ANIMATION_BUILDER_H_
@@ -0,0 +1,59 @@
//----------------------------------------------------------------------------//
// //
// ozz-animation is hosted at http://github.com/guillaumeblanc/ozz-animation //
// and distributed under the MIT License (MIT). //
// //
// Copyright (c) Guillaume Blanc //
// //
// Permission is hereby granted, free of charge, to any person obtaining a //
// copy of this software and associated documentation files (the "Software"), //
// to deal in the Software without restriction, including without limitation //
// the rights to use, copy, modify, merge, publish, distribute, sublicense, //
// and/or sell copies of the Software, and to permit persons to whom the //
// Software is 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 Software. //
// //
// THE SOFTWARE IS 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 SOFTWARE OR THE USE OR OTHER //
// DEALINGS IN THE SOFTWARE. //
// //
//----------------------------------------------------------------------------//
#ifndef OZZ_OZZ_ANIMATION_OFFLINE_ANIMATION_BUILDER_H_
#define OZZ_OZZ_ANIMATION_OFFLINE_ANIMATION_BUILDER_H_
#include "ozz/base/memory/unique_ptr.h"
namespace ozz {
namespace animation {
// Forward declares the runtime animation type.
class Animation;
namespace offline {
// Forward declares the offline animation type.
struct RawAnimation;
// Defines the class responsible of building runtime animation instances from
// offline raw animations.
// No optimization at all is performed on the raw animation.
class AnimationBuilder {
public:
// Creates an Animation based on _raw_animation and *this builder parameters.
// Returns a valid Animation on success.
// See RawAnimation::Validate() for more details about failure reasons.
// The animation is returned as an unique_ptr as ownership is given back to
// the caller.
unique_ptr<Animation> operator()(const RawAnimation& _raw_animation) const;
};
} // namespace offline
} // namespace animation
} // namespace ozz
#endif // OZZ_OZZ_ANIMATION_OFFLINE_ANIMATION_BUILDER_H_
@@ -0,0 +1,103 @@
//----------------------------------------------------------------------------//
// //
// ozz-animation is hosted at http://github.com/guillaumeblanc/ozz-animation //
// and distributed under the MIT License (MIT). //
// //
// Copyright (c) Guillaume Blanc //
// //
// Permission is hereby granted, free of charge, to any person obtaining a //
// copy of this software and associated documentation files (the "Software"), //
// to deal in the Software without restriction, including without limitation //
// the rights to use, copy, modify, merge, publish, distribute, sublicense, //
// and/or sell copies of the Software, and to permit persons to whom the //
// Software is 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 Software. //
// //
// THE SOFTWARE IS 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 SOFTWARE OR THE USE OR OTHER //
// DEALINGS IN THE SOFTWARE. //
// //
//----------------------------------------------------------------------------//
#ifndef OZZ_OZZ_ANIMATION_OFFLINE_ANIMATION_OPTIMIZER_H_
#define OZZ_OZZ_ANIMATION_OFFLINE_ANIMATION_OPTIMIZER_H_
#include "ozz/base/containers/map.h"
namespace ozz {
namespace animation {
// Forward declare runtime skeleton type.
class Skeleton;
namespace offline {
// Forward declare offline animation type.
struct RawAnimation;
// Defines the class responsible of optimizing an offline raw animation
// instance. Optimization is performed using a key frame reduction technique. It
// deciamtes redundant / interpolable key frames, within error tolerances given
// as input. The optimizer takes into account for each joint the error
// generated on its whole child hierarchy. This allows for example to take into
// consideration the error generated on a finger when optimizing the shoulder. A
// small error on the shoulder can be magnified when propagated to the finger
// indeed.
// It's possible to override optimization settings for a joint. This implicitely
// have an effect on the whole chain, up to that joint. This allows for example
// to have aggressive optimization for a whole skeleton, except for the chain
// that leads to the hand if user wants it to be precise. Default optimization
// tolerances are set in order to favor quality over runtime performances and
// memory footprint.
class AnimationOptimizer {
public:
// Initializes the optimizer with default tolerances (favoring quality).
AnimationOptimizer();
// Optimizes _input using *this parameters. _skeleton is required to evaluate
// optimization error along joint hierarchy (see hierarchical_tolerance).
// Returns true on success and fills _output animation with the optimized
// version of _input animation.
// *_output must be a valid RawAnimation instance.
// Returns false on failure and resets _output to an empty animation.
// See RawAnimation::Validate() for more details about failure reasons.
bool operator()(const RawAnimation& _input, const Skeleton& _skeleton,
RawAnimation* _output) const;
// Optimization settings.
struct Setting {
// Default settings
Setting()
: tolerance(1e-3f), // 1mm
distance(1e-1f) // 10cm
{}
Setting(float _tolerance, float _distance)
: tolerance(_tolerance), distance(_distance) {}
// The maximum error that an optimization is allowed to generate on a whole
// joint hierarchy.
float tolerance;
// The distance (from the joint) at which error is measured (if bigger that
// joint hierarchy). This allows to emulate effect on skinning.
float distance;
};
// Golbal optimization settings. These settings apply to all joints of the
// hierarchy, unless overriden by joint specific settings.
Setting setting;
// Per joint override of optimization settings.
typedef ozz::map<int, Setting> JointsSetting;
JointsSetting joints_setting_override;
};
} // namespace offline
} // namespace animation
} // namespace ozz
#endif // OZZ_OZZ_ANIMATION_OFFLINE_ANIMATION_OPTIMIZER_H_
@@ -0,0 +1,170 @@
//----------------------------------------------------------------------------//
// //
// ozz-animation is hosted at http://github.com/guillaumeblanc/ozz-animation //
// and distributed under the MIT License (MIT). //
// //
// Copyright (c) Guillaume Blanc //
// //
// Permission is hereby granted, free of charge, to any person obtaining a //
// copy of this software and associated documentation files (the "Software"), //
// to deal in the Software without restriction, including without limitation //
// the rights to use, copy, modify, merge, publish, distribute, sublicense, //
// and/or sell copies of the Software, and to permit persons to whom the //
// Software is 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 Software. //
// //
// THE SOFTWARE IS 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 SOFTWARE OR THE USE OR OTHER //
// DEALINGS IN THE SOFTWARE. //
// //
//----------------------------------------------------------------------------//
#ifndef OZZ_OZZ_ANIMATION_OFFLINE_FBX_FBX_H_
#define OZZ_OZZ_ANIMATION_OFFLINE_FBX_FBX_H_
#include <fbxsdk.h>
#include "ozz/base/maths/simd_math.h"
#include "ozz/base/maths/transform.h"
namespace ozz {
namespace math {
struct Transform;
} // namespace math
namespace animation {
namespace offline {
namespace fbx {
// Manages FbxManager instance.
class FbxManagerInstance {
public:
// Instantiates FbxManager.
FbxManagerInstance();
// Destroys FbxManager.
~FbxManagerInstance();
// Cast operator to get internal FbxManager instance.
operator FbxManager*() const { return fbx_manager_; }
private:
FbxManager* fbx_manager_;
};
// Default io settings used to import a scene.
class FbxDefaultIOSettings {
public:
// Instantiates default settings.
explicit FbxDefaultIOSettings(const FbxManagerInstance& _manager);
// De-instantiates default settings.
virtual ~FbxDefaultIOSettings();
// Get FbxIOSettings instance.
FbxIOSettings* settings() const { return io_settings_; }
// Cast operator to get internal FbxIOSettings instance.
operator FbxIOSettings*() const { return io_settings_; }
private:
FbxIOSettings* io_settings_;
};
// Io settings used to import an animation from a scene.
class FbxAnimationIOSettings : public FbxDefaultIOSettings {
public:
FbxAnimationIOSettings(const FbxManagerInstance& _manager);
};
// Io settings used to import a skeleton from a scene.
class FbxSkeletonIOSettings : public FbxDefaultIOSettings {
public:
FbxSkeletonIOSettings(const FbxManagerInstance& _manager);
};
// Implements axis system and unit system conversion helper, from any Fbx system
// to ozz system (FbxAxisSystem::eYAxis, FbxAxisSystem::eParityOdd,
// FbxAxisSystem::eRightHanded, meter).
// While Fbx sdk FbxAxisSystem::ConvertScene and FbxSystem::ConvertScene only
// affect scene root, this class functions can be used to bake nodes, vertices,
// animations transformations...
class FbxSystemConverter {
public:
// Initialize converter with fbx scene systems.
FbxSystemConverter(const FbxAxisSystem& _from_axis,
const FbxSystemUnit& _from_unit);
// Converts a fbx matrix to an ozz Float4x4 matrix, in ozz axis and unit
// systems, using _m' = C * _m * (C-1) operation.
math::Float4x4 ConvertMatrix(const FbxAMatrix& _m) const;
// Converts fbx matrix to an ozz transform, in ozz axis and unit systems,
// using _m' = C * _m * (C-1) operation.
// Can return false if matrix isn't affine.
bool ConvertTransform(const FbxAMatrix& _m,
math::Transform* _transform) const;
// Converts fbx FbxVector4 point to an ozz Float3, in ozz axis and unit
// systems, using _p' = C * _p operation.
math::Float3 ConvertPoint(const FbxVector4& _p) const;
// Converts fbx FbxVector4 vector to an ozz Float3, in ozz axis and unit
// systems, using _p' = ((C-1)-T) * _p operation. Normals are converted
// using the inverse transpose matrix to support non-uniform scale
// transformations.
math::Float3 ConvertVector(const FbxVector4& _p) const;
private:
// The matrix used to convert from "from" axis/unit to ozz coordinate system
// base.
math::Float4x4 convert_;
// The inverse of convert_ matrix.
math::Float4x4 inverse_convert_;
// The transpose inverse of convert_ matrix.
math::Float4x4 inverse_transpose_convert_;
};
// Loads a scene from a Fbx file.
class FbxSceneLoader {
public:
// Loads the scene that can then be obtained with scene() function.
FbxSceneLoader(const char* _filename, const char* _password,
const FbxManagerInstance& _manager,
const FbxDefaultIOSettings& _io_settings);
FbxSceneLoader(FbxStream* _stream, const char* _password,
const FbxManagerInstance& _manager,
const FbxDefaultIOSettings& _io_settings);
~FbxSceneLoader();
// Returns a valid scene if fbx import was successful, nullptr otherwise.
FbxScene* scene() const { return scene_; }
// Returns a valid converter if fbx import was successful, nullptr otherwise.
FbxSystemConverter* converter() { return converter_; }
private:
void ImportScene(FbxImporter* _importer, const bool _initialized,
const char* _password, const FbxManagerInstance& _manager,
const FbxDefaultIOSettings& _io_settings);
// Scene instance that was loaded from the file.
FbxScene* scene_;
// Axis and unit conversion helper.
FbxSystemConverter* converter_;
};
} // namespace fbx
} // namespace offline
} // namespace animation
} // namespace ozz
#endif // OZZ_OZZ_ANIMATION_OFFLINE_FBX_FBX_H_
@@ -0,0 +1,90 @@
//----------------------------------------------------------------------------//
// //
// ozz-animation is hosted at http://github.com/guillaumeblanc/ozz-animation //
// and distributed under the MIT License (MIT). //
// //
// Copyright (c) Guillaume Blanc //
// //
// Permission is hereby granted, free of charge, to any person obtaining a //
// copy of this software and associated documentation files (the "Software"), //
// to deal in the Software without restriction, including without limitation //
// the rights to use, copy, modify, merge, publish, distribute, sublicense, //
// and/or sell copies of the Software, and to permit persons to whom the //
// Software is 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 Software. //
// //
// THE SOFTWARE IS 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 SOFTWARE OR THE USE OR OTHER //
// DEALINGS IN THE SOFTWARE. //
// //
//----------------------------------------------------------------------------//
#ifndef OZZ_OZZ_ANIMATION_OFFLINE_FBX_FBX_ANIMATION_H_
#define OZZ_OZZ_ANIMATION_OFFLINE_FBX_FBX_ANIMATION_H_
#include "ozz/animation/offline/fbx/fbx.h"
#include "ozz/animation/offline/tools/import2ozz.h"
#include "ozz/base/containers/string.h"
#include "ozz/base/containers/vector.h"
namespace ozz {
namespace animation {
class Skeleton;
namespace offline {
struct RawAnimation;
struct RawFloatTrack;
struct RawFloat2Track;
struct RawFloat3Track;
struct RawFloat4Track;
struct RawquaternionTrack;
namespace fbx {
OzzImporter::AnimationNames GetAnimationNames(FbxSceneLoader& _scene_loader);
bool ExtractAnimation(const char* _animation_name,
FbxSceneLoader& _scene_loader, const Skeleton& _skeleton,
float _sampling_rate, RawAnimation* _animation);
OzzImporter::NodeProperties GetNodeProperties(FbxSceneLoader& _scene_loader,
const char* _node_name);
bool ExtractTrack(const char* _animation_name, const char* _node_name,
const char* _track_name,
OzzImporter::NodeProperty::Type _type,
FbxSceneLoader& _scene_loader, float _sampling_rate,
RawFloatTrack* _track);
bool ExtractTrack(const char* _animation_name, const char* _node_name,
const char* _track_name,
OzzImporter::NodeProperty::Type _type,
FbxSceneLoader& _scene_loader, float _sampling_rate,
RawFloat2Track* _track);
bool ExtractTrack(const char* _animation_name, const char* _node_name,
const char* _track_name,
OzzImporter::NodeProperty::Type _type,
FbxSceneLoader& _scene_loader, float _sampling_rate,
RawFloat3Track* _track);
bool ExtractTrack(const char* _animation_name, const char* _node_name,
const char* _track_name,
OzzImporter::NodeProperty::Type _type,
FbxSceneLoader& _scene_loader, float _sampling_rate,
RawFloat4Track* _track);
} // namespace fbx
} // namespace offline
} // namespace animation
} // namespace ozz
#endif // OZZ_OZZ_ANIMATION_OFFLINE_FBX_FBX_ANIMATION_H_
@@ -0,0 +1,50 @@
//----------------------------------------------------------------------------//
// //
// ozz-animation is hosted at http://github.com/guillaumeblanc/ozz-animation //
// and distributed under the MIT License (MIT). //
// //
// Copyright (c) Guillaume Blanc //
// //
// Permission is hereby granted, free of charge, to any person obtaining a //
// copy of this software and associated documentation files (the "Software"), //
// to deal in the Software without restriction, including without limitation //
// the rights to use, copy, modify, merge, publish, distribute, sublicense, //
// and/or sell copies of the Software, and to permit persons to whom the //
// Software is 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 Software. //
// //
// THE SOFTWARE IS 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 SOFTWARE OR THE USE OR OTHER //
// DEALINGS IN THE SOFTWARE. //
// //
//----------------------------------------------------------------------------//
#ifndef OZZ_OZZ_ANIMATION_OFFLINE_FBX_FBX_SKELETON_H_
#define OZZ_OZZ_ANIMATION_OFFLINE_FBX_FBX_SKELETON_H_
#include "ozz/animation/offline/fbx/fbx.h"
#include "ozz/animation/offline/tools/import2ozz.h"
namespace ozz {
namespace animation {
namespace offline {
struct RawSkeleton;
namespace fbx {
bool ExtractSkeleton(FbxSceneLoader& _loader,
const OzzImporter::NodeType& _types,
RawSkeleton* _skeleton);
} // namespace fbx
} // namespace offline
} // namespace animation
} // namespace ozz
#endif // OZZ_OZZ_ANIMATION_OFFLINE_FBX_FBX_SKELETON_H_
@@ -0,0 +1,159 @@
//----------------------------------------------------------------------------//
// //
// ozz-animation is hosted at http://github.com/guillaumeblanc/ozz-animation //
// and distributed under the MIT License (MIT). //
// //
// Copyright (c) Guillaume Blanc //
// //
// Permission is hereby granted, free of charge, to any person obtaining a //
// copy of this software and associated documentation files (the "Software"), //
// to deal in the Software without restriction, including without limitation //
// the rights to use, copy, modify, merge, publish, distribute, sublicense, //
// and/or sell copies of the Software, and to permit persons to whom the //
// Software is 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 Software. //
// //
// THE SOFTWARE IS 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 SOFTWARE OR THE USE OR OTHER //
// DEALINGS IN THE SOFTWARE. //
// //
//----------------------------------------------------------------------------//
#ifndef OZZ_OZZ_ANIMATION_OFFLINE_RAW_ANIMATION_H_
#define OZZ_OZZ_ANIMATION_OFFLINE_RAW_ANIMATION_H_
#include "ozz/base/containers/string.h"
#include "ozz/base/containers/vector.h"
#include "ozz/base/io/archive_traits.h"
#include "ozz/base/maths/quaternion.h"
#include "ozz/base/maths/vec_float.h"
namespace ozz {
namespace animation {
namespace offline {
// Offline animation type.
// This animation type is not intended to be used in run time. It is used to
// define the offline animation object that can be converted to the runtime
// animation using the AnimationBuilder.
// This animation structure exposes tracks of keyframes. Keyframes are defined
// with a time and a value which can either be a translation (3 float x, y, z),
// a rotation (a quaternion) or scale coefficient (3 floats x, y, z). Tracks are
// defined as a set of three different std::vectors (translation, rotation and
// scales). Animation structure is then a vector of tracks, along with a
// duration value.
// Finally the RawAnimation structure exposes Validate() function to check that
// it is valid, meaning that all the following rules are respected:
// 1. Animation duration is greater than 0.
// 2. Keyframes' time are sorted in a strict ascending order.
// 3. Keyframes' time are all within [0,animation duration] range.
// Animations that would fail this validation will fail to be converted by the
// AnimationBuilder.
struct RawAnimation {
// Constructs a valid RawAnimation with a 1s default duration.
RawAnimation();
// Tests for *this validity.
// Returns true if animation data (duration, tracks) is valid:
// 1. Animation duration is greater than 0.
// 2. Keyframes' time are sorted in a strict ascending order.
// 3. Keyframes' time are all within [0,animation duration] range.
bool Validate() const;
// Get the estimated animation's size in bytes.
size_t size() const;
// Defines a raw translation key frame.
struct TranslationKey {
// Key frame time.
float time;
// Key frame value.
typedef math::Float3 Value;
Value value;
// Provides identity transformation for a translation key.
static math::Float3 identity() { return math::Float3::zero(); }
};
// Defines a raw rotation key frame.
struct RotationKey {
// Key frame time.
float time;
// Key frame value.
typedef math::Quaternion Value;
math::Quaternion value;
// Provides identity transformation for a rotation key.
static math::Quaternion identity() { return math::Quaternion::identity(); }
};
// Defines a raw scaling key frame.
struct ScaleKey {
// Key frame time.
float time;
// Key frame value.
typedef math::Float3 Value;
math::Float3 value;
// Provides identity transformation for a scale key.
static math::Float3 identity() { return math::Float3::one(); }
};
// Defines a track of key frames for a bone, including translation, rotation
// and scale.
struct JointTrack {
typedef ozz::vector<TranslationKey> Translations;
Translations translations;
typedef ozz::vector<RotationKey> Rotations;
Rotations rotations;
typedef ozz::vector<ScaleKey> Scales;
Scales scales;
// Validates track. See RawAnimation::Validate for more details.
// Use an infinite value for _duration if unknown. This will validate
// keyframe orders, but not maximum duration.
bool Validate(float _duration) const;
};
// Returns the number of tracks of this animation.
int num_tracks() const { return static_cast<int>(tracks.size()); }
// Stores per joint JointTrack, ie: per joint animation key-frames.
// tracks_.size() gives the number of animated joints.
ozz::vector<JointTrack> tracks;
// The duration of the animation. All the keys of a valid RawAnimation are in
// the range [0,duration].
float duration;
// Name of the animation.
ozz::string name;
};
} // namespace offline
} // namespace animation
namespace io {
OZZ_IO_TYPE_VERSION(3, animation::offline::RawAnimation)
OZZ_IO_TYPE_TAG("ozz-raw_animation", animation::offline::RawAnimation)
// Should not be called directly but through io::Archive << and >> operators.
template <>
struct Extern<animation::offline::RawAnimation> {
static void Save(OArchive& _archive,
const animation::offline::RawAnimation* _animations,
size_t _count);
static void Load(IArchive& _archive,
animation::offline::RawAnimation* _animations, size_t _count,
uint32_t _version);
};
} // namespace io
} // namespace ozz
#endif // OZZ_OZZ_ANIMATION_OFFLINE_RAW_ANIMATION_H_

Some files were not shown because too many files have changed in this diff Show More